/[dynamips]/trunk/ppc32_x86_trans.c
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Diff of /trunk/ppc32_x86_trans.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

upstream/dynamips-0.2.7-RC1/ppc32_x86_trans.c revision 7 by dpavlin, Sat Oct 6 16:23:47 2007 UTC trunk/ppc32_x86_trans.c revision 12 by dpavlin, Sat Oct 6 16:45:40 2007 UTC
# Line 13  Line 13 
13  #include <fcntl.h>  #include <fcntl.h>
14    
15  #include "cpu.h"  #include "cpu.h"
16    #include "jit_op.h"
17  #include "ppc32_jit.h"  #include "ppc32_jit.h"
18  #include "ppc32_x86_trans.h"  #include "ppc32_x86_trans.h"
19  #include "memory.h"  #include "memory.h"
20    
21    /* %esp adjustment (for MacOS X) */
22    #define STACK_ADJUST  12
23    
24    /* ======================================================================= */
25    
26  /* Macros for CPU structure access */  /* Macros for CPU structure access */
27  #define REG_OFFSET(reg)   (OFFSET(cpu_ppc_t,gpr[(reg)]))  #define REG_OFFSET(reg)   (OFFSET(cpu_ppc_t,gpr[(reg)]))
28  #define MEMOP_OFFSET(op)  (OFFSET(cpu_ppc_t,mem_op_fn[(op)]))  #define MEMOP_OFFSET(op)  (OFFSET(cpu_ppc_t,mem_op_fn[(op)]))
# Line 25  Line 31 
31     static int ppc32_emit_##name(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b, \     static int ppc32_emit_##name(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b, \
32                                  ppc_insn_t insn)                                  ppc_insn_t insn)
33    
34  /* Dump regs */  /* EFLAGS to Condition Register (CR) field - signed */
35  static void ppc32_emit_dump_regs(ppc32_jit_tcb_t *b);  static m_uint32_t eflags_to_cr_signed[256] = {
36       0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04,
37       0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04,
38       0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04,
39       0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04,
40       0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04,
41       0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04,
42       0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04,
43       0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04,
44       0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02,
45       0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02,
46       0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02,
47       0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02,
48       0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02,
49       0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02,
50       0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02,
51       0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02,
52       0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08,
53       0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08,
54       0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08,
55       0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08,
56       0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08,
57       0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08,
58       0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08,
59       0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08,
60       0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
61       0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
62       0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
63       0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
64       0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
65       0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
66       0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
67       0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
68    };
69    
70    /* EFLAGS to Condition Register (CR) field - unsigned */
71    static m_uint32_t eflags_to_cr_unsigned[256] = {
72       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
73       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
74       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
75       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
76       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
77       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
78       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
79       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
80       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
81       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
82       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
83       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
84       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
85       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
86       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
87       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
88       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
89       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
90       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
91       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
92       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
93       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
94       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
95       0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08,
96       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
97       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
98       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
99       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
100       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
101       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
102       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
103       0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a, 0x02, 0x0a,
104    };
105    
106    /* Emit unhandled instruction code */
107    static int ppc32_emit_unknown(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b,
108                                  ppc_insn_t opcode);
109    
110  /* Load a 32 bit immediate value */  /* Load a 32 bit immediate value */
111  static inline void ppc32_load_imm(ppc32_jit_tcb_t *b,u_int reg,m_uint32_t val)  static forced_inline void ppc32_load_imm(u_char **ptr,u_int reg,m_uint32_t val)
112  {  {
113     if (val)     if (val)
114        x86_mov_reg_imm(b->jit_ptr,reg,val);        x86_mov_reg_imm(*ptr,reg,val);
115     else     else
116        x86_alu_reg_reg(b->jit_ptr,X86_XOR,reg,reg);        x86_alu_reg_reg(*ptr,X86_XOR,reg,reg);
117  }  }
118    
119  /* Set the Instruction Address (IA) register */  /* Set the Instruction Address (IA) register */
120  void ppc32_set_ia(ppc32_jit_tcb_t *b,m_uint32_t new_ia)  void ppc32_set_ia(u_char **ptr,m_uint32_t new_ia)
121  {  {
122     x86_mov_membase_imm(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,ia),new_ia,4);     x86_mov_membase_imm(*ptr,X86_EDI,OFFSET(cpu_ppc_t,ia),new_ia,4);
123  }  }
124    
125  /* Set the Link Register (LR) */  /* Set the Link Register (LR) */
126  void ppc32_set_lr(ppc32_jit_tcb_t *b,m_uint32_t new_lr)  static void ppc32_set_lr(jit_op_t *iop,m_uint32_t new_lr)
127  {    {  
128     x86_mov_membase_imm(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,lr),new_lr,4);     x86_mov_membase_imm(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,lr),new_lr,4);
129    }
130    
131    /*
132     * Try to branch directly to the specified JIT block without returning to
133     * main loop.
134     */
135    static void ppc32_try_direct_far_jump(cpu_ppc_t *cpu,jit_op_t *iop,
136                                          m_uint32_t new_ia)
137    {
138       m_uint32_t new_page,ia_hash,ia_offset;
139       u_char *test1,*test2,*test3;
140    
141       /* Indicate that we throw %esi, %edx */
142       ppc32_op_emit_alter_host_reg(cpu,X86_ESI);
143       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
144    
145       new_page = new_ia & PPC32_MIN_PAGE_MASK;
146       ia_offset = (new_ia & PPC32_MIN_PAGE_IMASK) >> 2;
147       ia_hash = ppc32_jit_get_ia_hash(new_ia);
148    
149       /* Get JIT block info in %edx */
150       x86_mov_reg_membase(iop->ob_ptr,X86_EBX,
151                           X86_EDI,OFFSET(cpu_ppc_t,exec_blk_map),4);
152       x86_mov_reg_membase(iop->ob_ptr,X86_EDX,X86_EBX,ia_hash*sizeof(void *),4);
153    
154       /* no JIT block found ? */
155       x86_test_reg_reg(iop->ob_ptr,X86_EDX,X86_EDX);
156       test1 = iop->ob_ptr;
157       x86_branch8(iop->ob_ptr, X86_CC_Z, 0, 1);
158    
159       /* Check block IA */
160       x86_mov_reg_imm(iop->ob_ptr,X86_ESI,new_page);
161       x86_alu_reg_membase(iop->ob_ptr,X86_CMP,X86_ESI,X86_EDX,
162                           OFFSET(ppc32_jit_tcb_t,start_ia));
163       test2 = iop->ob_ptr;
164       x86_branch8(iop->ob_ptr, X86_CC_NE, 0, 1);
165    
166       /* Jump to the code */
167       x86_mov_reg_membase(iop->ob_ptr,X86_ESI,
168                           X86_EDX,OFFSET(ppc32_jit_tcb_t,jit_insn_ptr),4);
169       x86_mov_reg_membase(iop->ob_ptr,X86_EBX,
170                           X86_ESI,ia_offset * sizeof(void *),4);
171      
172       x86_test_reg_reg(iop->ob_ptr,X86_EBX,X86_EBX);
173       test3 = iop->ob_ptr;
174       x86_branch8(iop->ob_ptr, X86_CC_Z, 0, 1);
175       x86_jump_reg(iop->ob_ptr,X86_EBX);
176    
177       /* Returns to caller... */
178       x86_patch(test1,iop->ob_ptr);
179       x86_patch(test2,iop->ob_ptr);
180       x86_patch(test3,iop->ob_ptr);
181    
182       ppc32_set_ia(&iop->ob_ptr,new_ia);
183       ppc32_jit_tcb_push_epilog(&iop->ob_ptr);
184  }  }
185    
186  /* Set Jump */  /* Set Jump */
187  static void ppc32_set_jump(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b,  static void ppc32_set_jump(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b,jit_op_t *iop,
188                             m_uint32_t new_ia,int local_jump)                             m_uint32_t new_ia,int local_jump)
189  {        {      
190     int return_to_caller = FALSE;     int return_to_caller = FALSE;
# Line 60  static void ppc32_set_jump(cpu_ppc_t *cp Line 194  static void ppc32_set_jump(cpu_ppc_t *cp
194     if (cpu->sym_trace && !local_jump)     if (cpu->sym_trace && !local_jump)
195        return_to_caller = TRUE;        return_to_caller = TRUE;
196  #endif  #endif
197          
198     if (!return_to_caller && ppc32_jit_tcb_local_addr(b,new_ia,&jump_ptr)) {     if (!return_to_caller && ppc32_jit_tcb_local_addr(b,new_ia,&jump_ptr)) {
199        if (jump_ptr) {        ppc32_jit_tcb_record_patch(b,iop,iop->ob_ptr,new_ia);
200           x86_jump_code(b->jit_ptr,jump_ptr);        x86_jump32(iop->ob_ptr,0);
201       } else {
202          if (cpu->exec_blk_direct_jump) {
203             /* Block lookup optimization */
204             ppc32_try_direct_far_jump(cpu,iop,new_ia);
205        } else {        } else {
206           ppc32_jit_tcb_record_patch(b,b->jit_ptr,new_ia);           ppc32_set_ia(&iop->ob_ptr,new_ia);
207           x86_jump32(b->jit_ptr,0);           ppc32_jit_tcb_push_epilog(&iop->ob_ptr);
208        }        }
    } else {  
       /* save PC */  
       ppc32_set_ia(b,new_ia);  
   
       /* address is in another block, for now, returns to caller */  
       ppc32_jit_tcb_push_epilog(b);  
209     }     }
210  }  }
211    
212  /* Load the Condition Register (CR) into the specified host register */  /* Jump to the next page */
213  static forced_inline void ppc32_load_cr(ppc32_jit_tcb_t *b,u_int host_reg)  void ppc32_set_page_jump(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b)
214  {  {
215     x86_mov_reg_membase(b->jit_ptr,host_reg,X86_EDI,OFFSET(cpu_ppc_t,cr),4);     jit_op_t *iop,*op_list = NULL;
 }  
216    
217  /* Store the Condition Register (CR) from the specified host register */     cpu->gen->jit_op_current = &op_list;
218  static forced_inline void ppc32_store_cr(ppc32_jit_tcb_t *b,u_int host_reg)  
219  {     iop = ppc32_op_emit_insn_output(cpu,4,"set_page_jump");
220     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,cr),host_reg,4);     ppc32_set_jump(cpu,b,iop,b->start_ia + PPC32_MIN_PAGE_SIZE,FALSE);
221       ppc32_op_insn_output(b,iop);
222    
223       jit_op_free_list(cpu->gen,op_list);
224       cpu->gen->jit_op_current = NULL;
225  }  }
226    
227  /* Load a GPR into the specified host register */  /* Load a GPR into the specified host register */
228  static forced_inline void ppc32_load_gpr(ppc32_jit_tcb_t *b,u_int host_reg,  static forced_inline void ppc32_load_gpr(u_char **ptr,u_int host_reg,
229                                           u_int ppc_reg)                                           u_int ppc_reg)
230  {  {
231     x86_mov_reg_membase(b->jit_ptr,host_reg,X86_EDI,REG_OFFSET(ppc_reg),4);     x86_mov_reg_membase(*ptr,host_reg,X86_EDI,REG_OFFSET(ppc_reg),4);
232  }  }
233    
234  /* Store contents for a host register into a GPR register */  /* Store contents for a host register into a GPR register */
235  static forced_inline void ppc32_store_gpr(ppc32_jit_tcb_t *b,u_int ppc_reg,  static forced_inline void ppc32_store_gpr(u_char **ptr,u_int ppc_reg,
236                                            u_int host_reg)                                            u_int host_reg)
237  {  {
238     x86_mov_membase_reg(b->jit_ptr,X86_EDI,REG_OFFSET(ppc_reg),host_reg,4);     x86_mov_membase_reg(*ptr,X86_EDI,REG_OFFSET(ppc_reg),host_reg,4);
239  }  }
240    
241  /* Apply an ALU operation on a GPR register and a host register */  /* Apply an ALU operation on a GPR register and a host register */
242  static forced_inline void ppc32_alu_gpr(ppc32_jit_tcb_t *b,u_int op,  static forced_inline void ppc32_alu_gpr(u_char **ptr,u_int op,
243                                          u_int host_reg,u_int ppc_reg)                                          u_int host_reg,u_int ppc_reg)
244  {  {
245     x86_alu_reg_membase(b->jit_ptr,op,host_reg,X86_EDI,REG_OFFSET(ppc_reg));     x86_alu_reg_membase(*ptr,op,host_reg,X86_EDI,REG_OFFSET(ppc_reg));
246  }  }
247    
248  /*  /*
249   * Update CR from %eflags   * Update CR from %eflags
250   * %eax, %ecx, %edx, %esi are modified.   * %eax, %edx, %esi are modified.
251   */   */
 #define PPC32_CR_LT_BIT  3  
 #define PPC32_CR_GT_BIT  2  
 #define PPC32_CR_EQ_BIT  1  
 #define PPC32_CR_SO_BIT  0  
   
252  static void ppc32_update_cr(ppc32_jit_tcb_t *b,int field,int is_signed)  static void ppc32_update_cr(ppc32_jit_tcb_t *b,int field,int is_signed)
253  {  {
254     m_uint32_t cr_mask;     /* Get status bits from EFLAGS */
255     u_int cfb;     x86_mov_reg_imm(b->jit_ptr,X86_EAX,0);
256       x86_lahf(b->jit_ptr);
257       x86_xchg_ah_al(b->jit_ptr);
258    
259     cr_mask = 0xF0000000 >> (field << 2);     if (is_signed)
260     cfb = 28 - (field << 2);        x86_mov_reg_imm(b->jit_ptr,X86_EDX,eflags_to_cr_signed);
261       else
262          x86_mov_reg_imm(b->jit_ptr,X86_EDX,eflags_to_cr_unsigned);
263    
264     x86_set_reg(b->jit_ptr,X86_CC_LT,X86_EAX,is_signed);     x86_mov_reg_memindex(b->jit_ptr,X86_EAX,X86_EDX,0,X86_EAX,2,4);
    x86_set_reg(b->jit_ptr,X86_CC_GT,X86_ECX,is_signed);  
    x86_set_reg(b->jit_ptr,X86_CC_Z,X86_EDX,is_signed);  
   
    x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EAX,(cfb + PPC32_CR_LT_BIT));  
    x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_ECX,(cfb + PPC32_CR_GT_BIT));  
    x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EDX,(cfb + PPC32_CR_EQ_BIT));  
   
    x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EAX,X86_ECX);  
    x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EAX,X86_EDX);  
   
    /* Load Condition Register */  
    x86_mov_reg_membase(b->jit_ptr,X86_EDX,X86_EDI,OFFSET(cpu_ppc_t,cr),4);  
    x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EDX,~cr_mask);  
    x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,cr_mask);  
    x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EDX,X86_EAX);  
265    
266     /* Check XER Summary of Overflow and report it */     /* Check XER Summary of Overflow and report it */
267     x86_mov_reg_membase(b->jit_ptr,X86_ECX,X86_EDI,OFFSET(cpu_ppc_t,xer),4);     x86_mov_reg_membase(b->jit_ptr,X86_EDX,X86_EDI,OFFSET(cpu_ppc_t,xer),4);
268     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ECX,PPC32_XER_SO);     //x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,PPC32_XER_SO);
269     x86_shift_reg_imm(b->jit_ptr,X86_SHR,X86_ECX,(field << 2) + 3);     //x86_shift_reg_imm(b->jit_ptr,X86_SHR,X86_ESI,PPC32_XER_SO_BIT);
270     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EDX,X86_ECX);     //x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EAX,X86_ESI);
271    
272     /* Store modified CR */     /* Store modified CR field */
273     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,cr),X86_EDX,4);     x86_mov_membase_reg(b->jit_ptr,X86_EDI,PPC32_CR_FIELD_OFFSET(field),
274                           X86_EAX,4);
275  }  }
276    
277  /*  /*
278   * Update CR0 from %eflags   * Update CR0 from %eflags
279   * %eax, %ecx, %edx, %esi are modified.   * %eax, %edx, %esi are modified.
280   */   */
281  static void ppc32_update_cr0(ppc32_jit_tcb_t *b)  static void ppc32_update_cr0(ppc32_jit_tcb_t *b)
282  {  {
283     ppc32_update_cr(b,0,TRUE);     ppc32_update_cr(b,0,TRUE);
284  }  }
285    
286    /* Indicate registers modified by ppc32_update_cr() functions */
287    void ppc32_update_cr_set_altered_hreg(cpu_ppc_t *cpu)
288    {
289       /* Throw %eax and %edx, which are modifed by ppc32_update_cr() */
290       ppc32_op_emit_alter_host_reg(cpu,X86_EAX);
291       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
292    }
293    
294  /* Basic C call */  /* Basic C call */
295  static forced_inline void ppc32_emit_basic_c_call(ppc32_jit_tcb_t *b,void *f)  static forced_inline
296    void ppc32_emit_basic_c_call(u_char **ptr,void *f)
297  {  {
298     x86_mov_reg_imm(b->jit_ptr,X86_EBX,f);     x86_mov_reg_imm(*ptr,X86_EBX,f);
299     x86_call_reg(b->jit_ptr,X86_EBX);     x86_call_reg(*ptr,X86_EBX);
300  }  }
301    
302  /* Emit a simple call to a C function without any parameter */  /* Emit a simple call to a C function without any parameter */
303  static void ppc32_emit_c_call(ppc32_jit_tcb_t *b,void *f)  static void ppc32_emit_c_call(ppc32_jit_tcb_t *b,jit_op_t *iop,void *f)
304  {    {  
305     ppc32_set_ia(b,b->start_ia+((b->ppc_trans_pos-1)<<2));     ppc32_set_ia(&iop->ob_ptr,b->start_ia+(b->ppc_trans_pos << 2));
306     ppc32_emit_basic_c_call(b,f);     ppc32_emit_basic_c_call(&iop->ob_ptr,f);
307    }
308    
309    /* ======================================================================== */
310    
311    /* Initialize register mapping */
312    void ppc32_jit_init_hreg_mapping(cpu_ppc_t *cpu)
313    {
314       int avail_hregs[] = { X86_ESI, X86_EAX, X86_ECX, X86_EDX, -1 };
315       struct hreg_map *map;
316       int i,hreg;
317    
318       cpu->hreg_map_list = cpu->hreg_lru = NULL;
319    
320       /* Add the available registers to the map list */
321       for(i=0;avail_hregs[i]!=-1;i++) {
322          hreg = avail_hregs[i];
323          map = &cpu->hreg_map[hreg];
324    
325          /* Initialize mapping. At the beginning, no PPC reg is mapped */
326          map->flags = 0;
327          map->hreg  = hreg;
328          map->vreg  = -1;
329          ppc32_jit_insert_hreg_mru(cpu,map);
330       }
331    
332       /* Clear PPC registers mapping */
333       for(i=0;i<PPC32_GPR_NR;i++)
334          cpu->ppc_reg_map[i] = -1;
335    }
336    
337    /* Allocate a specific temp register */
338    static int ppc32_jit_get_tmp_hreg(cpu_ppc_t *cpu)
339    {
340       return(X86_EBX);
341  }  }
342    
343    /* ======================================================================== */
344    /* JIT operations (specific to target CPU).                                 */
345    /* ======================================================================== */
346    
347    /* INSN_OUTPUT */
348    void ppc32_op_insn_output(ppc32_jit_tcb_t *b,jit_op_t *op)
349    {
350       op->ob_final = b->jit_ptr;
351       memcpy(b->jit_ptr,op->ob_data,op->ob_ptr - op->ob_data);
352       b->jit_ptr += op->ob_ptr - op->ob_data;
353    
354       if ((op->ob_ptr - op->ob_data) >= jit_op_blk_sizes[op->ob_size_index]) {
355          printf("ppc32_op_insn_output: FAILURE: count=%d, size=%d\n",
356                 op->ob_ptr - op->ob_data, jit_op_blk_sizes[op->ob_size_index]);
357       }
358    }
359    
360    /* LOAD_GPR: p[0] = %host_reg, p[1] = %ppc_reg */
361    void ppc32_op_load_gpr(ppc32_jit_tcb_t *b,jit_op_t *op)
362    {
363       if (op->param[0] != JIT_OP_INV_REG)
364          ppc32_load_gpr(&b->jit_ptr,op->param[0],op->param[1]);
365    }
366    
367    /* STORE_GPR: p[0] = %host_reg, p[1] = %ppc_reg */
368    void ppc32_op_store_gpr(ppc32_jit_tcb_t *b,jit_op_t *op)
369    {
370       if (op->param[0] != JIT_OP_INV_REG)
371          ppc32_store_gpr(&b->jit_ptr,op->param[1],op->param[0]);
372    }
373    
374    /* UPDATE_FLAGS: p[0] = cr_field, p[1] = is_signed */
375    void ppc32_op_update_flags(ppc32_jit_tcb_t *b,jit_op_t *op)
376    {
377       if (op->param[0] != JIT_OP_INV_REG)
378          ppc32_update_cr(b,op->param[0],op->param[1]);
379    }
380    
381    /* MOVE_HOST_REG: p[0] = %host_dst_reg, p[1] = %host_src_reg */
382    void ppc32_op_move_host_reg(ppc32_jit_tcb_t *b,jit_op_t *op)
383    {
384       if ((op->param[0] != JIT_OP_INV_REG) && (op->param[1] != JIT_OP_INV_REG))
385          x86_mov_reg_reg(b->jit_ptr,op->param[0],op->param[1],4);
386    }
387    
388    /* SET_HOST_REG_IMM32: p[0] = %host_reg, p[1] = imm32 */
389    void ppc32_op_set_host_reg_imm32(ppc32_jit_tcb_t *b,jit_op_t *op)
390    {
391       if (op->param[0] != JIT_OP_INV_REG)
392          ppc32_load_imm(&b->jit_ptr,op->param[0],op->param[1]);
393    }
394    
395    /* ======================================================================== */
396    
397  /* Memory operation */  /* Memory operation */
398  static void ppc32_emit_memop(ppc32_jit_tcb_t *b,int op,int base,int offset,  static void ppc32_emit_memop(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b,
399                               int target,int update)                               int op,int base,int offset,int target,int update)
400  {  {
401     m_uint32_t val = sign_extend(offset,16);     m_uint32_t val = sign_extend(offset,16);
402     u_char *test1;     jit_op_t *iop;
403    
404       /*
405        * Since an exception can be triggered, clear JIT state. This allows
406        * to use branch target tag (we can directly branch on this instruction).
407        */
408       ppc32_op_emit_basic_opcode(cpu,JIT_OP_BRANCH_TARGET);
409       ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
410    
411       iop = ppc32_op_emit_insn_output(cpu,5,"memop");
412    
413     /* Save PC for exception handling */     /* Save PC for exception handling */
414     ppc32_set_ia(b,b->start_ia+((b->ppc_trans_pos-1)<<2));     ppc32_set_ia(&iop->ob_ptr,b->start_ia+(b->ppc_trans_pos << 2));
415    
416     /* EDX = sign-extended offset */     /* EDX = sign-extended offset */
417     ppc32_load_imm(b,X86_EDX,val);     ppc32_load_imm(&iop->ob_ptr,X86_EDX,val);
418    
419     /* EDX = GPR[base] + sign-extended offset */     /* EDX = GPR[base] + sign-extended offset */
420     if (update || (base != 0))     if (update || (base != 0))
421        ppc32_alu_gpr(b,X86_ADD,X86_EDX,base);        ppc32_alu_gpr(&iop->ob_ptr,X86_ADD,X86_EDX,base);
422    
423     if (update)     if (update)
424        x86_mov_reg_reg(b->jit_ptr,X86_ESI,X86_EDX,4);        x86_mov_reg_reg(iop->ob_ptr,X86_ESI,X86_EDX,4);
425    
426     /* ECX = target register */     /* ECX = target register */
427     x86_mov_reg_imm(b->jit_ptr,X86_ECX,target);     x86_mov_reg_imm(iop->ob_ptr,X86_ECX,target);
428        
429     /* EAX = CPU instance pointer */     /* EAX = CPU instance pointer */
430     x86_mov_reg_reg(b->jit_ptr,X86_EAX,X86_EDI,4);     x86_mov_reg_reg(iop->ob_ptr,X86_EAX,X86_EDI,4);
431    
432     /* Call memory function */     /* Call memory function */
433     x86_call_membase(b->jit_ptr,X86_EDI,MEMOP_OFFSET(op));     x86_alu_reg_imm(iop->ob_ptr,X86_SUB,X86_ESP,STACK_ADJUST);
434       x86_call_membase(iop->ob_ptr,X86_EDI,MEMOP_OFFSET(op));
435     /* Exception ? */     x86_alu_reg_imm(iop->ob_ptr,X86_ADD,X86_ESP,STACK_ADJUST);
436     x86_test_reg_reg(b->jit_ptr,X86_EAX,X86_EAX);    
    test1 = b->jit_ptr;  
    x86_branch8(b->jit_ptr, X86_CC_Z, 0, 1);  
    ppc32_jit_tcb_push_epilog(b);  
    x86_patch(test1,b->jit_ptr);  
   
437     if (update)     if (update)
438        ppc32_store_gpr(b,base,X86_ESI);        ppc32_store_gpr(&iop->ob_ptr,base,X86_ESI);
439  }  }
440    
441  /* Memory operation (indexed) */  /* Memory operation (indexed) */
442  static void ppc32_emit_memop_idx(ppc32_jit_tcb_t *b,int op,int ra,int rb,  static void ppc32_emit_memop_idx(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b,
443                                   int target,int update)                                   int op,int ra,int rb,int target,int update)
444  {  {
445     u_char *test1;     jit_op_t *iop;
446    
447       /*
448        * Since an exception can be triggered, clear JIT state. This allows
449        * to use branch target tag (we can directly branch on this instruction).
450        */
451       ppc32_op_emit_basic_opcode(cpu,JIT_OP_BRANCH_TARGET);
452       ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
453    
454       iop = ppc32_op_emit_insn_output(cpu,5,"memop_idx");
455    
456     /* Save PC for exception handling */     /* Save PC for exception handling */
457     ppc32_set_ia(b,b->start_ia+((b->ppc_trans_pos-1)<<2));     ppc32_set_ia(&iop->ob_ptr,b->start_ia+(b->ppc_trans_pos << 2));
458    
459     /* EDX = $rb */     /* EDX = $rb */
460     ppc32_load_gpr(b,X86_EDX,rb);     ppc32_load_gpr(&iop->ob_ptr,X86_EDX,rb);
461    
462     /* EDX = $rb + $ra */     /* EDX = $rb + $ra */
463     if (update || (ra != 0))     if (update || (ra != 0))
464        ppc32_alu_gpr(b,X86_ADD,X86_EDX,ra);        ppc32_alu_gpr(&iop->ob_ptr,X86_ADD,X86_EDX,ra);
465    
466     if (update)     if (update)
467        x86_mov_reg_reg(b->jit_ptr,X86_ESI,X86_EDX,4);        x86_mov_reg_reg(iop->ob_ptr,X86_ESI,X86_EDX,4);
468    
469     /* ECX = target register */     /* ECX = target register */
470     x86_mov_reg_imm(b->jit_ptr,X86_ECX,target);     x86_mov_reg_imm(iop->ob_ptr,X86_ECX,target);
471        
472     /* EAX = CPU instance pointer */     /* EAX = CPU instance pointer */
473     x86_mov_reg_reg(b->jit_ptr,X86_EAX,X86_EDI,4);     x86_mov_reg_reg(iop->ob_ptr,X86_EAX,X86_EDI,4);
474    
475     /* Call memory function */     /* Call memory function */
476     x86_call_membase(b->jit_ptr,X86_EDI,MEMOP_OFFSET(op));     x86_alu_reg_imm(iop->ob_ptr,X86_SUB,X86_ESP,STACK_ADJUST);
477       x86_call_membase(iop->ob_ptr,X86_EDI,MEMOP_OFFSET(op));
478     /* Exception ? */     x86_alu_reg_imm(iop->ob_ptr,X86_ADD,X86_ESP,STACK_ADJUST);
479     x86_test_reg_reg(b->jit_ptr,X86_EAX,X86_EAX);    
    test1 = b->jit_ptr;  
    x86_branch8(b->jit_ptr, X86_CC_Z, 0, 1);  
    ppc32_jit_tcb_push_epilog(b);  
    x86_patch(test1,b->jit_ptr);  
   
480     if (update)     if (update)
481        ppc32_store_gpr(b,ra,X86_ESI);        ppc32_store_gpr(&iop->ob_ptr,ra,X86_ESI);
482  }  }
483    
484  typedef void (*memop_fast_access)(ppc32_jit_tcb_t *b,int target);  typedef void (*memop_fast_access)(jit_op_t *iop,int target);
485    
486  /* Fast LBZ */  /* Fast LBZ */
487  static void ppc32_memop_fast_lbz(ppc32_jit_tcb_t *b,int target)  static void ppc32_memop_fast_lbz(jit_op_t *iop,int target)
488  {  {
489     x86_clear_reg(b->jit_ptr,X86_ECX);     x86_clear_reg(iop->ob_ptr,X86_ECX);
490     x86_mov_reg_memindex(b->jit_ptr,X86_ECX,X86_EAX,0,X86_EBX,0,1);     x86_mov_reg_memindex(iop->ob_ptr,X86_ECX,X86_EAX,0,X86_EBX,0,1);
491     ppc32_store_gpr(b,target,X86_ECX);     ppc32_store_gpr(&iop->ob_ptr,target,X86_ECX);
492  }  }
493    
494  /* Fast STB */  /* Fast STB */
495  static void ppc32_memop_fast_stb(ppc32_jit_tcb_t *b,int target)  static void ppc32_memop_fast_stb(jit_op_t *iop,int target)
496  {  {
497     ppc32_load_gpr(b,X86_EDX,target);     ppc32_load_gpr(&iop->ob_ptr,X86_EDX,target);
498     x86_mov_memindex_reg(b->jit_ptr,X86_EAX,0,X86_EBX,0,X86_EDX,1);     x86_mov_memindex_reg(iop->ob_ptr,X86_EAX,0,X86_EBX,0,X86_EDX,1);
499  }  }
500    
501  /* Fast LWZ */  /* Fast LWZ */
502  static void ppc32_memop_fast_lwz(ppc32_jit_tcb_t *b,int target)  static void ppc32_memop_fast_lwz(jit_op_t *iop,int target)
503  {  {
504     x86_mov_reg_memindex(b->jit_ptr,X86_EAX,X86_EAX,0,X86_EBX,0,4);     x86_mov_reg_memindex(iop->ob_ptr,X86_EAX,X86_EAX,0,X86_EBX,0,4);
505     x86_bswap(b->jit_ptr,X86_EAX);     x86_bswap(iop->ob_ptr,X86_EAX);
506     ppc32_store_gpr(b,target,X86_EAX);     ppc32_store_gpr(&iop->ob_ptr,target,X86_EAX);
507  }  }
508    
509  /* Fast STW */  /* Fast STW */
510  static void ppc32_memop_fast_stw(ppc32_jit_tcb_t *b,int target)  static void ppc32_memop_fast_stw(jit_op_t *iop,int target)
511  {  {
512     ppc32_load_gpr(b,X86_EDX,target);     ppc32_load_gpr(&iop->ob_ptr,X86_EDX,target);
513     x86_bswap(b->jit_ptr,X86_EDX);     x86_bswap(iop->ob_ptr,X86_EDX);
514     x86_mov_memindex_reg(b->jit_ptr,X86_EAX,0,X86_EBX,0,X86_EDX,4);     x86_mov_memindex_reg(iop->ob_ptr,X86_EAX,0,X86_EBX,0,X86_EDX,4);
515  }  }
516    
517  /* Fast memory operation */  /* Fast memory operation */
518  static void ppc32_emit_memop_fast(ppc32_jit_tcb_t *b,int write_op,int opcode,  static void ppc32_emit_memop_fast(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b,
519                                      int write_op,int opcode,
520                                    int base,int offset,int target,                                    int base,int offset,int target,
521                                    memop_fast_access op_handler)                                    memop_fast_access op_handler)
522  {  {
523     m_uint32_t val = sign_extend(offset,16);     m_uint32_t val = sign_extend(offset,16);
524     u_char *test1,*test2,*p_exception,*p_exit;     u_char *test1,*test2,*p_exit,*p_fast_exit;
525       jit_op_t *iop;
526    
527       /*
528        * Since an exception can be triggered, clear JIT state. This allows
529        * to use branch target tag (we can directly branch on this instruction).
530        */
531       ppc32_op_emit_basic_opcode(cpu,JIT_OP_BRANCH_TARGET);
532       ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
533    
534       iop = ppc32_op_emit_insn_output(cpu,5,"memop_fast");
535    
536     test2 = NULL;     test2 = NULL;
537    
538     /* EBX = sign-extended offset */     if (val != 0) {
539     ppc32_load_imm(b,X86_EBX,val);        /* EBX = sign-extended offset */
540          ppc32_load_imm(&iop->ob_ptr,X86_EBX,val);
541    
542          /* EBX = GPR[base] + sign-extended offset */
543          if (base != 0)
544             ppc32_alu_gpr(&iop->ob_ptr,X86_ADD,X86_EBX,base);
545       } else {
546          if (base != 0)
547             ppc32_load_gpr(&iop->ob_ptr,X86_EBX,base);
548          else
549             ppc32_load_imm(&iop->ob_ptr,X86_EBX,0);
550       }
551    
552    #if 0
553       /* ======= zzz ======= */
554       {
555          u_char *testZ;
556    
557          x86_mov_reg_reg(iop->ob_ptr,X86_ESI,X86_EBX,4);
558          x86_alu_reg_imm(iop->ob_ptr,X86_AND,X86_ESI,PPC32_MIN_PAGE_MASK);
559          x86_alu_reg_membase(iop->ob_ptr,X86_CMP,X86_ESI,X86_EDI,
560                              OFFSET(cpu_ppc_t,vtlb[base].vaddr));
561          testZ = iop->ob_ptr;
562          x86_branch8(iop->ob_ptr, X86_CC_NZ, 0, 1);
563    
564          x86_alu_reg_imm(iop->ob_ptr,X86_AND,X86_EBX,PPC32_MIN_PAGE_IMASK);
565          x86_mov_reg_membase(iop->ob_ptr,X86_EAX,
566                              X86_EDI,OFFSET(cpu_ppc_t,vtlb[base].haddr),4);
567    
568     /* EBX = GPR[base] + sign-extended offset */        /* Memory access */
569     if (base != 0)        op_handler(iop,target);
570        ppc32_alu_gpr(b,X86_ADD,X86_EBX,base);  
571          p_fast_exit = iop->ob_ptr;
572          x86_jump8(iop->ob_ptr,0);
573    
574          x86_patch(testZ,iop->ob_ptr);
575       }
576    #endif
577    
578     /* EAX = mts32_entry index */     /* EAX = mts32_entry index */
579     x86_mov_reg_reg(b->jit_ptr,X86_EAX,X86_EBX,4);     x86_mov_reg_reg(iop->ob_ptr,X86_EAX,X86_EBX,4);
580     x86_shift_reg_imm(b->jit_ptr,X86_SHR,X86_EAX,MTS32_HASH_SHIFT);     x86_shift_reg_imm(iop->ob_ptr,X86_SHR,X86_EAX,MTS32_HASH_SHIFT);
581     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,MTS32_HASH_MASK);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,X86_EAX,MTS32_HASH_MASK);
582    
583     /* EDX = mts32_entry */     /* EDX = mts32_entry */
584     x86_mov_reg_membase(b->jit_ptr,X86_EDX,     x86_mov_reg_membase(iop->ob_ptr,X86_EDX,
585                         X86_EDI,OFFSET(cpu_ppc_t,mts_cache[PPC32_MTS_DCACHE]),                         X86_EDI,OFFSET(cpu_ppc_t,mts_cache[PPC32_MTS_DCACHE]),
586                         4);                         4);
587     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EAX,4);     x86_shift_reg_imm(iop->ob_ptr,X86_SHL,X86_EAX,4);
588     x86_alu_reg_reg(b->jit_ptr,X86_ADD,X86_EDX,X86_EAX);     x86_alu_reg_reg(iop->ob_ptr,X86_ADD,X86_EDX,X86_EAX);
589    
590     /* Compare virtual page address (ESI = vpage) */     /* Compare virtual page address (ESI = vpage) */
591     x86_mov_reg_reg(b->jit_ptr,X86_ESI,X86_EBX,4);     x86_mov_reg_reg(iop->ob_ptr,X86_ESI,X86_EBX,4);
592     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,PPC32_MIN_PAGE_MASK);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,X86_ESI,PPC32_MIN_PAGE_MASK);
593    
594     x86_alu_reg_membase(b->jit_ptr,X86_CMP,X86_ESI,X86_EDX,     x86_alu_reg_membase(iop->ob_ptr,X86_CMP,X86_ESI,X86_EDX,
595                         OFFSET(mts32_entry_t,gvpa));                         OFFSET(mts32_entry_t,gvpa));
596     test1 = b->jit_ptr;     test1 = iop->ob_ptr;
597     x86_branch8(b->jit_ptr, X86_CC_NZ, 0, 1);     x86_branch8(iop->ob_ptr, X86_CC_NZ, 0, 1);
598    
599     /* Test if we are writing to a COW page */     /* Test if we are writing to a COW page */
600     if (write_op) {     if (write_op) {
601        x86_test_membase_imm(b->jit_ptr,X86_EDX,OFFSET(mts32_entry_t,flags),        x86_test_membase_imm(iop->ob_ptr,X86_EDX,OFFSET(mts32_entry_t,flags),
602                             MTS_FLAG_COW);                             MTS_FLAG_COW|MTS_FLAG_EXEC);
603        test2 = b->jit_ptr;        test2 = iop->ob_ptr;
604        x86_branch8(b->jit_ptr, X86_CC_NZ, 0, 1);        x86_branch8(iop->ob_ptr, X86_CC_NZ, 0, 1);
605     }     }
606    
607     /* EBX = offset in page, EAX = Host Page Address */     /* EBX = offset in page, EAX = Host Page Address */
608     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,PPC32_MIN_PAGE_IMASK);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,X86_EBX,PPC32_MIN_PAGE_IMASK);
609     x86_mov_reg_membase(b->jit_ptr,X86_EAX,X86_EDX,OFFSET(mts32_entry_t,hpa),4);     x86_mov_reg_membase(iop->ob_ptr,X86_EAX,
610                           X86_EDX,OFFSET(mts32_entry_t,hpa),4);
611    
612    #if 0
613       /* zzz */
614       {
615          x86_mov_membase_reg(iop->ob_ptr,
616                              X86_EDI,OFFSET(cpu_ppc_t,vtlb[base].vaddr),
617                              X86_ESI,4);
618          x86_mov_membase_reg(iop->ob_ptr,
619                              X86_EDI,OFFSET(cpu_ppc_t,vtlb[base].haddr),
620                              X86_EAX,4);
621       }
622    #endif
623    
624     /* Memory access */     /* Memory access */
625     op_handler(b,target);     op_handler(iop,target);
626    
627     p_exit = b->jit_ptr;     p_exit = iop->ob_ptr;
628     x86_jump8(b->jit_ptr,0);     x86_jump8(iop->ob_ptr,0);
629    
630     /* === Slow lookup === */     /* === Slow lookup === */
631     x86_patch(test1,b->jit_ptr);     x86_patch(test1,iop->ob_ptr);
632     if (test2)     if (test2)
633        x86_patch(test2,b->jit_ptr);        x86_patch(test2,iop->ob_ptr);
634    
635     /* Update IA (EBX = vaddr) */     /* Update IA (EBX = vaddr) */
636     ppc32_set_ia(b,b->start_ia+((b->ppc_trans_pos-1)<<2));     ppc32_set_ia(&iop->ob_ptr,b->start_ia+(b->ppc_trans_pos << 2));
637    
638     /* EDX = virtual address */     /* EDX = virtual address */
639     x86_mov_reg_reg(b->jit_ptr,X86_EDX,X86_EBX,4);     x86_mov_reg_reg(iop->ob_ptr,X86_EDX,X86_EBX,4);
640    
641     /* ECX = target register */     /* ECX = target register */
642     x86_mov_reg_imm(b->jit_ptr,X86_ECX,target);     x86_mov_reg_imm(iop->ob_ptr,X86_ECX,target);
643    
644     /* EAX = CPU instance pointer */     /* EAX = CPU instance pointer */
645     x86_mov_reg_reg(b->jit_ptr,X86_EAX,X86_EDI,4);     x86_mov_reg_reg(iop->ob_ptr,X86_EAX,X86_EDI,4);
646    
647     /* Call memory function */     /* Call memory function */
648     x86_call_membase(b->jit_ptr,X86_EDI,MEMOP_OFFSET(opcode));     x86_alu_reg_imm(iop->ob_ptr,X86_SUB,X86_ESP,STACK_ADJUST);
649       x86_call_membase(iop->ob_ptr,X86_EDI,MEMOP_OFFSET(opcode));
650     /* Check for exception */     x86_alu_reg_imm(iop->ob_ptr,X86_ADD,X86_ESP,STACK_ADJUST);
651     x86_test_reg_reg(b->jit_ptr,X86_EAX,X86_EAX);    
652     p_exception = b->jit_ptr;     x86_patch(p_exit,iop->ob_ptr);
    x86_branch8(b->jit_ptr, X86_CC_Z, 0, 1);  
    ppc32_jit_tcb_push_epilog(b);  
   
    x86_patch(p_exit,b->jit_ptr);  
    x86_patch(p_exception,b->jit_ptr);  
 }  
   
 /* Virtual Breakpoint */  
 void ppc32_emit_breakpoint(ppc32_jit_tcb_t *b)  
 {  
    x86_mov_reg_reg(b->jit_ptr,X86_EAX,X86_EDI,4);  
    ppc32_emit_c_call(b,ppc32_run_breakpoint);  
 }  
   
 /* Unknown opcode handler */  
 static asmlinkage void ppc32_unknown_opcode(cpu_ppc_t *cpu,m_uint32_t opcode)  
 {  
    printf("PPC32: unhandled opcode 0x%8.8x at 0x%8.8x (lr=0x%8.8x)\n",  
           opcode,cpu->ia,cpu->lr);  
653    
654     ppc32_dump_regs(cpu->gen);     /* zzz */
655     exit(1);  #if 0
656       x86_patch(p_fast_exit,iop->ob_ptr);
657    #endif
658  }  }
659    
660  /* Emit unhandled instruction code */  /* Emit unhandled instruction code */
# Line 397  static int ppc32_emit_unknown(cpu_ppc_t Line 662  static int ppc32_emit_unknown(cpu_ppc_t
662                                ppc_insn_t opcode)                                ppc_insn_t opcode)
663  {  {
664     u_char *test1;     u_char *test1;
665       jit_op_t *iop;
666    
667  #if 0           iop = ppc32_op_emit_insn_output(cpu,3,"unknown");
    x86_mov_reg_imm(b->jit_ptr,X86_EAX,opcode);  
    x86_alu_reg_imm(b->jit_ptr,X86_SUB,X86_ESP,4);  
    x86_push_reg(b->jit_ptr,X86_EAX);  
    x86_push_reg(b->jit_ptr,X86_EDI);  
    ppc32_emit_c_call(b,ppc32_unknown_opcode);  
    x86_alu_reg_imm(b->jit_ptr,X86_ADD,X86_ESP,12);  
 #endif  
668    
669     /* Update IA */     /* Update IA */
670     ppc32_set_ia(b,b->start_ia+((b->ppc_trans_pos-1)<<2));     ppc32_set_ia(&iop->ob_ptr,b->start_ia+(b->ppc_trans_pos << 2));
671    
672     /* Fallback to non-JIT mode */     /* Fallback to non-JIT mode */
673     x86_mov_reg_reg(b->jit_ptr,X86_EAX,X86_EDI,4);     x86_alu_reg_imm(iop->ob_ptr,X86_SUB,X86_ESP,STACK_ADJUST);
674     x86_mov_reg_imm(b->jit_ptr,X86_EDX,opcode);     x86_mov_reg_reg(iop->ob_ptr,X86_EAX,X86_EDI,4);
675       x86_mov_reg_imm(iop->ob_ptr,X86_EDX,opcode);
676    
677       ppc32_emit_basic_c_call(&iop->ob_ptr,ppc32_exec_single_insn_ext);
678       x86_alu_reg_imm(iop->ob_ptr,X86_ADD,X86_ESP,STACK_ADJUST);
679      
680       x86_test_reg_reg(iop->ob_ptr,X86_EAX,X86_EAX);
681       test1 = iop->ob_ptr;
682       x86_branch8(iop->ob_ptr, X86_CC_Z, 0, 1);
683       ppc32_jit_tcb_push_epilog(&iop->ob_ptr);
684    
685     ppc32_emit_c_call(b,ppc32_exec_single_insn_ext);     x86_patch(test1,iop->ob_ptr);
    x86_test_reg_reg(b->jit_ptr,X86_EAX,X86_EAX);  
    test1 = b->jit_ptr;  
    x86_branch8(b->jit_ptr, X86_CC_Z, 0, 1);  
    ppc32_jit_tcb_push_epilog(b);  
686    
687     x86_patch(test1,b->jit_ptr);     /* Signal this as an EOB to reset JIT state */
688       ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
689     return(0);     return(0);
690  }  }
691    
692    /* Virtual Breakpoint */
693    void ppc32_emit_breakpoint(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b)
694    {
695       jit_op_t *iop;
696    
697       iop = ppc32_op_emit_insn_output(cpu,2,"breakpoint");
698    
699       x86_alu_reg_imm(iop->ob_ptr,X86_SUB,X86_ESP,STACK_ADJUST);
700       x86_mov_reg_reg(iop->ob_ptr,X86_EAX,X86_EDI,4);
701       ppc32_emit_c_call(b,iop,ppc32_run_breakpoint);
702       x86_alu_reg_imm(iop->ob_ptr,X86_ADD,X86_ESP,STACK_ADJUST);
703    
704       /* Signal this as an EOB to to reset JIT state */
705       ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
706    }
707    
708  /* Dump regs */  /* Dump regs */
709  static void ppc32_emit_dump_regs(ppc32_jit_tcb_t *b)  static void ppc32_emit_dump_regs(cpu_ppc_t *cpu,ppc32_jit_tcb_t *b)
710  {    {  
711     x86_mov_reg_membase(b->jit_ptr,X86_EAX,X86_EDI,OFFSET(cpu_ppc_t,gen),4);     jit_op_t *iop;
712     x86_push_reg(b->jit_ptr,X86_EAX);    
713     ppc32_emit_c_call(b,ppc32_dump_regs);     iop = ppc32_op_emit_insn_output(cpu,2,"dump_regs");
714     x86_alu_reg_imm(b->jit_ptr,X86_ADD,X86_ESP,4);  
715       x86_mov_reg_membase(iop->ob_ptr,X86_EAX,X86_EDI,OFFSET(cpu_ppc_t,gen),4);
716      
717       x86_alu_reg_imm(iop->ob_ptr,X86_SUB,X86_ESP,STACK_ADJUST-4);
718       x86_push_reg(iop->ob_ptr,X86_EAX);
719       ppc32_emit_c_call(b,iop,ppc32_dump_regs);
720       x86_alu_reg_imm(iop->ob_ptr,X86_ADD,X86_ESP,STACK_ADJUST);
721    
722       /* Signal this as an EOB to to reset JIT state */
723       ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
724  }  }
725    
726  /* Increment the number of executed instructions (performance debugging) */  /* Increment the number of executed instructions (performance debugging) */
727  void ppc32_inc_perf_counter(ppc32_jit_tcb_t *b)  void ppc32_inc_perf_counter(cpu_ppc_t *cpu)
728  {  {
729     x86_alu_membase_imm(b->jit_ptr,X86_ADD,     jit_op_t *iop;
730                         X86_EDI,OFFSET(cpu_ppc_t,perf_counter),1);    
731     x86_alu_membase_imm(b->jit_ptr,X86_ADC,     iop = ppc32_op_emit_insn_output(cpu,1,"perf_cnt");
732                         X86_EDI,OFFSET(cpu_ppc_t,perf_counter)+4,0);     x86_inc_membase(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,perf_counter));
733  }  }
734    
735  /* ======================================================================== */  /* ======================================================================== */
# Line 447  void ppc32_inc_perf_counter(ppc32_jit_tc Line 737  void ppc32_inc_perf_counter(ppc32_jit_tc
737  /* BLR - Branch to Link Register */  /* BLR - Branch to Link Register */
738  DECLARE_INSN(BLR)  DECLARE_INSN(BLR)
739  {  {
740     x86_mov_reg_membase(b->jit_ptr,X86_EDX,X86_EDI,OFFSET(cpu_ppc_t,lr),4);     jit_op_t *iop;
741     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,ia),X86_EDX,4);     int hreg;
742    
743       ppc32_jit_start_hreg_seq(cpu,"blr");
744       hreg = ppc32_jit_alloc_hreg(cpu,-1);
745       ppc32_op_emit_alter_host_reg(cpu,hreg);
746    
747       iop = ppc32_op_emit_insn_output(cpu,2,"blr");
748    
749       x86_mov_reg_membase(iop->ob_ptr,hreg,X86_EDI,OFFSET(cpu_ppc_t,lr),4);
750       x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,ia),hreg,4);
751    
752     /* set the return address */     /* set the return address */
753     if (insn & 1)     if (insn & 1)
754        ppc32_set_lr(b,b->start_ia + (b->ppc_trans_pos << 2));        ppc32_set_lr(iop,b->start_ia + ((b->ppc_trans_pos+1) << 2));
755    
756     ppc32_jit_tcb_push_epilog(b);     ppc32_jit_tcb_push_epilog(&iop->ob_ptr);
757       ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
758       ppc32_op_emit_branch_target(cpu,b,b->start_ia+((b->ppc_trans_pos+1) << 2));
759    
760       ppc32_jit_close_hreg_seq(cpu);
761     return(0);     return(0);
762  }  }
763    
764  /* BCTR - Branch to Count Register */  /* BCTR - Branch to Count Register */
765  DECLARE_INSN(BCTR)  DECLARE_INSN(BCTR)
766  {  {
767     x86_mov_reg_membase(b->jit_ptr,X86_EDX,X86_EDI,OFFSET(cpu_ppc_t,ctr),4);     jit_op_t *iop;
768     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,ia),X86_EDX,4);     int hreg;
769    
770       ppc32_jit_start_hreg_seq(cpu,"bctr");
771       hreg = ppc32_jit_alloc_hreg(cpu,-1);
772       ppc32_op_emit_alter_host_reg(cpu,hreg);
773    
774       iop = ppc32_op_emit_insn_output(cpu,2,"bctr");
775    
776       x86_mov_reg_membase(iop->ob_ptr,hreg,X86_EDI,OFFSET(cpu_ppc_t,ctr),4);
777       x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,ia),hreg,4);
778    
779     /* set the return address */     /* set the return address */
780     if (insn & 1)     if (insn & 1)
781        ppc32_set_lr(b,b->start_ia + (b->ppc_trans_pos << 2));        ppc32_set_lr(iop,b->start_ia + ((b->ppc_trans_pos+1) << 2));
782    
783     ppc32_jit_tcb_push_epilog(b);     ppc32_jit_tcb_push_epilog(&iop->ob_ptr);
784       ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
785       ppc32_op_emit_branch_target(cpu,b,b->start_ia+((b->ppc_trans_pos+1) << 2));
786    
787       ppc32_jit_close_hreg_seq(cpu);
788     return(0);     return(0);
789  }  }
790    
# Line 476  DECLARE_INSN(BCTR) Line 792  DECLARE_INSN(BCTR)
792  DECLARE_INSN(MFLR)  DECLARE_INSN(MFLR)
793  {  {
794     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
795         int hreg_rd;
796     x86_mov_reg_membase(b->jit_ptr,X86_EDX,X86_EDI,OFFSET(cpu_ppc_t,lr),4);     jit_op_t *iop;
797     ppc32_store_gpr(b,rd,X86_EDX);  
798       ppc32_jit_start_hreg_seq(cpu,"mflr");
799       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
800       iop = ppc32_op_emit_insn_output(cpu,1,"mflr");
801    
802       x86_mov_reg_membase(iop->ob_ptr,hreg_rd,X86_EDI,OFFSET(cpu_ppc_t,lr),4);
803       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
804    
805       ppc32_jit_close_hreg_seq(cpu);
806     return(0);     return(0);
807  }  }
808    
# Line 486  DECLARE_INSN(MFLR) Line 810  DECLARE_INSN(MFLR)
810  DECLARE_INSN(MTLR)  DECLARE_INSN(MTLR)
811  {  {
812     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
813       int hreg_rs;
814       jit_op_t *iop;
815      
816       ppc32_jit_start_hreg_seq(cpu,"mtlr");
817       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
818       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
819    
820     ppc32_load_gpr(b,X86_EDX,rs);     iop = ppc32_op_emit_insn_output(cpu,1,"mtlr");
821     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,lr),X86_EDX,4);     x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,lr),hreg_rs,4);
822    
823       ppc32_jit_close_hreg_seq(cpu);
824     return(0);     return(0);
825  }  }
826    
# Line 496  DECLARE_INSN(MTLR) Line 828  DECLARE_INSN(MTLR)
828  DECLARE_INSN(MFCTR)  DECLARE_INSN(MFCTR)
829  {  {
830     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
831       int hreg_rd;
832       jit_op_t *iop;
833        
834     x86_mov_reg_membase(b->jit_ptr,X86_EDX,X86_EDI,OFFSET(cpu_ppc_t,ctr),4);     ppc32_jit_start_hreg_seq(cpu,"mfctr");
835     ppc32_store_gpr(b,rd,X86_EDX);     hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
836    
837       iop = ppc32_op_emit_insn_output(cpu,1,"mfctr");
838    
839       x86_mov_reg_membase(iop->ob_ptr,hreg_rd,X86_EDI,OFFSET(cpu_ppc_t,ctr),4);
840       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
841    
842       ppc32_jit_close_hreg_seq(cpu);
843     return(0);     return(0);
844  }  }
845    
# Line 506  DECLARE_INSN(MFCTR) Line 847  DECLARE_INSN(MFCTR)
847  DECLARE_INSN(MTCTR)  DECLARE_INSN(MTCTR)
848  {  {
849     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
850       int hreg_rs;
851       jit_op_t *iop;
852    
853       ppc32_jit_start_hreg_seq(cpu,"mtctr");
854       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
855       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
856    
857     ppc32_load_gpr(b,X86_EDX,rs);     iop = ppc32_op_emit_insn_output(cpu,1,"mtctr");
858     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,ctr),X86_EDX,4);     x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,ctr),hreg_rs,4);
859    
860       ppc32_jit_close_hreg_seq(cpu);
861     return(0);     return(0);
862  }  }
863    
# Line 516  DECLARE_INSN(MTCTR) Line 865  DECLARE_INSN(MTCTR)
865  DECLARE_INSN(MFTBU)  DECLARE_INSN(MFTBU)
866  {  {
867     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
868       int hreg_rd;
869       jit_op_t *iop;
870    
871       ppc32_jit_start_hreg_seq(cpu,"mftbu");
872       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
873    
874       iop = ppc32_op_emit_insn_output(cpu,1,"mftbu");
875    
876       x86_mov_reg_membase(iop->ob_ptr,hreg_rd,X86_EDI,OFFSET(cpu_ppc_t,tb)+4,4);
877       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
878    
879     x86_mov_reg_membase(b->jit_ptr,X86_EDX,X86_EDI,OFFSET(cpu_ppc_t,tb)+4,4);     ppc32_jit_close_hreg_seq(cpu);
    ppc32_store_gpr(b,rd,X86_EDX);  
880     return(0);     return(0);
881  }  }
882    
# Line 528  DECLARE_INSN(MFTBU) Line 886  DECLARE_INSN(MFTBU)
886  DECLARE_INSN(MFTBL)  DECLARE_INSN(MFTBL)
887  {  {
888     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
889       int hreg_rd,hreg_t0;
890       jit_op_t *iop;
891    
892       ppc32_jit_start_hreg_seq(cpu,"mftbl");
893       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
894       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
895    
896       iop = ppc32_op_emit_insn_output(cpu,3,"mftbl");
897    
898       x86_mov_reg_membase(iop->ob_ptr,hreg_rd,X86_EDI,OFFSET(cpu_ppc_t,tb),4);
899    
900     /* Increment the time base register */     /* Increment the time base register */
901     x86_mov_reg_membase(b->jit_ptr,X86_EDX,X86_EDI,OFFSET(cpu_ppc_t,tb),4);     x86_mov_reg_membase(iop->ob_ptr,hreg_rd,X86_EDI,OFFSET(cpu_ppc_t,tb),4);
902     x86_mov_reg_membase(b->jit_ptr,X86_EBX,X86_EDI,OFFSET(cpu_ppc_t,tb)+4,4);     x86_mov_reg_membase(iop->ob_ptr,hreg_t0,X86_EDI,OFFSET(cpu_ppc_t,tb)+4,4);
903     x86_alu_reg_imm(b->jit_ptr,X86_ADD,X86_EDX,PPC32_TB_INCREMENT);     x86_alu_reg_imm(iop->ob_ptr,X86_ADD,hreg_rd,PPC32_TB_INCREMENT);
904     x86_alu_reg_imm(b->jit_ptr,X86_ADC,X86_EBX,0);     x86_alu_reg_imm(iop->ob_ptr,X86_ADC,hreg_t0,0);
905     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,tb),X86_EDX,4);     x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,tb),hreg_rd,4);
906     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,tb)+4,X86_EBX,4);     x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,tb)+4,hreg_t0,4);
907    
908     ppc32_store_gpr(b,rd,X86_EDX);     ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
909    
910       ppc32_jit_close_hreg_seq(cpu);
911     return(0);     return(0);
912  }  }
913    
# Line 547  DECLARE_INSN(ADD) Line 917  DECLARE_INSN(ADD)
917     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
918     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
919     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
920       int hreg_rd,hreg_ra,hreg_rb;
921       jit_op_t *iop;
922    
923     /* $rd = $ra + $rb */     /* $rd = $ra + $rb */
924     ppc32_load_gpr(b,X86_EBX,ra);     ppc32_jit_start_hreg_seq(cpu,"add");
925     ppc32_alu_gpr(b,X86_ADD,X86_EBX,rb);     hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
926     ppc32_store_gpr(b,rd,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
927       hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
928    
929       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
930       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
931    
932       iop = ppc32_op_emit_insn_output(cpu,2,"add");
933    
934       if (rd == ra)
935          x86_alu_reg_reg(iop->ob_ptr,X86_ADD,hreg_rd,hreg_rb);
936       else if (rd == rb)
937          x86_alu_reg_reg(iop->ob_ptr,X86_ADD,hreg_rd,hreg_ra);
938       else {
939          x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_ra,4);
940          x86_alu_reg_reg(iop->ob_ptr,X86_ADD,hreg_rd,hreg_rb);
941       }
942    
943       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
944    
945     if (insn & 1)     if (insn & 1)
946        ppc32_update_cr0(b);        ppc32_op_emit_update_flags(cpu,0,TRUE);
947            
948       ppc32_jit_close_hreg_seq(cpu);
949     return(0);     return(0);
950  }  }
951    
# Line 565  DECLARE_INSN(ADDC) Line 955  DECLARE_INSN(ADDC)
955     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
956     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
957     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
958       int hreg_rd,hreg_ra,hreg_rb,hreg_t0;
959       jit_op_t *iop;
960    
961     /* $rd = $ra + $rb */     /* $rd = $ra + $rb */
962     ppc32_load_gpr(b,X86_EBX,ra);     ppc32_jit_start_hreg_seq(cpu,"addc");
963     ppc32_alu_gpr(b,X86_ADD,X86_EBX,rb);     hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
964     ppc32_store_gpr(b,rd,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
965       hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
966    
967     /* store the carry flag */     /* store the carry flag */
968     x86_set_reg(b->jit_ptr,X86_CC_C,X86_EAX,FALSE);     hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
969     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,0x1);  
970     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),X86_EAX,4);     ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
971       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
972    
973       iop = ppc32_op_emit_insn_output(cpu,2,"addc");
974    
975       if (rd == ra)
976          x86_alu_reg_reg(iop->ob_ptr,X86_ADD,hreg_rd,hreg_rb);
977       else if (rd == rb)
978          x86_alu_reg_reg(iop->ob_ptr,X86_ADD,hreg_rd,hreg_ra);
979       else {
980          x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_ra,4);
981          x86_alu_reg_reg(iop->ob_ptr,X86_ADD,hreg_rd,hreg_rb);
982       }
983    
984       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
985      
986       x86_set_reg(iop->ob_ptr,X86_CC_C,hreg_t0,FALSE);
987       x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x1);
988       x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),
989                           hreg_t0,4);
990    
991     if (insn & 1) {     if (insn & 1) {
992        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);        x86_test_reg_reg(iop->ob_ptr,hreg_rd,hreg_rd);
993        ppc32_update_cr0(b);        ppc32_op_emit_update_flags(cpu,0,TRUE);
994     }     }
995          
996       ppc32_jit_close_hreg_seq(cpu);
997     return(0);     return(0);
998  }  }
999    
# Line 590  DECLARE_INSN(ADDE) Line 1003  DECLARE_INSN(ADDE)
1003     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
1004     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1005     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
1006       int hreg_ra,hreg_rb,hreg_rd,hreg_t0,hreg_t1;
1007       jit_op_t *iop;
1008    
1009     /* $ra + carry */     ppc32_jit_start_hreg_seq(cpu,"adde");
1010     ppc32_load_gpr(b,X86_ESI,ra);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1011     x86_alu_reg_membase(b->jit_ptr,X86_ADD,X86_ESI,     hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
1012                         X86_EDI,OFFSET(cpu_ppc_t,xer_ca));     hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
    x86_set_reg(b->jit_ptr,X86_CC_C,X86_EAX,FALSE);  
1013    
1014     /* add $rb */     hreg_t0 = ppc32_jit_alloc_hreg(cpu,-1);
1015     ppc32_alu_gpr(b,X86_ADD,X86_ESI,rb);     hreg_t1 = ppc32_jit_get_tmp_hreg(cpu);
    x86_set_reg(b->jit_ptr,X86_CC_C,X86_ECX,FALSE);  
1016    
1017     ppc32_store_gpr(b,rd,X86_ESI);     ppc32_op_emit_alter_host_reg(cpu,hreg_t0);
1018       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
1019       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
1020    
1021     /* store the carry flag */     iop = ppc32_op_emit_insn_output(cpu,3,"adde");
1022     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EAX,X86_ECX);  
1023     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,0x1);     /* $t0 = $ra + carry */
1024       x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_t1,hreg_t1);
1025       x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_ra,4);
1026    
1027       x86_alu_reg_membase(iop->ob_ptr,X86_ADD,hreg_t0,
1028                           X86_EDI,OFFSET(cpu_ppc_t,xer_ca));
1029       x86_set_reg(iop->ob_ptr,X86_CC_C,hreg_t1,FALSE);
1030       x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),hreg_t1,4);
1031    
1032     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),X86_EAX,4);     /* $t0 += $rb */
1033       x86_alu_reg_reg(iop->ob_ptr,X86_ADD,hreg_t0,hreg_rb);
1034       x86_set_reg(iop->ob_ptr,X86_CC_C,hreg_t1,FALSE);
1035       x86_alu_membase_reg(iop->ob_ptr,X86_OR,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),
1036                           hreg_t1);
1037    
1038     /* update cr0 */     /* update cr0 */
1039     if (insn & 1) {     if (insn & 1)
1040        x86_test_reg_reg(b->jit_ptr,X86_ESI,X86_ESI);        x86_test_reg_reg(iop->ob_ptr,hreg_t0,hreg_t0);
1041        ppc32_update_cr0(b);  
1042     }     x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_t0,4);
1043       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
1044    
1045       if (insn & 1)
1046          ppc32_op_emit_update_flags(cpu,0,TRUE);
1047    
1048       ppc32_jit_close_hreg_seq(cpu);
1049     return(0);     return(0);
1050  }  }
1051    
# Line 625  DECLARE_INSN(ADDI) Line 1056  DECLARE_INSN(ADDI)
1056     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1057     int imm = bits(insn,0,15);     int imm = bits(insn,0,15);
1058     m_uint32_t tmp = sign_extend_32(imm,16);     m_uint32_t tmp = sign_extend_32(imm,16);
1059       int hreg_rd,hreg_ra;
1060       jit_op_t *iop;
1061    
1062       /* $rd = $ra + imm */
1063       ppc32_jit_start_hreg_seq(cpu,"addi");
1064       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
1065    
1066     ppc32_load_imm(b,X86_EBX,tmp);     if (ra != 0) {
1067          hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1068          ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
1069    
1070          iop = ppc32_op_emit_insn_output(cpu,2,"addi");
1071    
1072          if (rd != ra)
1073             x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_ra,4);
1074    
1075          x86_alu_reg_imm(iop->ob_ptr,X86_ADD,hreg_rd,tmp);
1076       } else {
1077          iop = ppc32_op_emit_insn_output(cpu,1,"addi");
1078          ppc32_load_imm(&iop->ob_ptr,hreg_rd,tmp);
1079       }
1080    
1081     if (ra != 0)     ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
       x86_alu_reg_membase(b->jit_ptr,X86_ADD,X86_EBX,X86_EDI,REG_OFFSET(ra));  
1082    
1083     ppc32_store_gpr(b,rd,X86_EBX);     ppc32_jit_close_hreg_seq(cpu);
1084     return(0);     return(0);
1085  }  }
1086    
# Line 642  DECLARE_INSN(ADDIC) Line 1091  DECLARE_INSN(ADDIC)
1091     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1092     int imm = bits(insn,0,15);     int imm = bits(insn,0,15);
1093     m_uint32_t tmp = sign_extend_32(imm,16);     m_uint32_t tmp = sign_extend_32(imm,16);
1094       int hreg_rd,hreg_ra;
1095       jit_op_t *iop;
1096    
1097       /* $rd = $ra + imm */
1098       ppc32_jit_start_hreg_seq(cpu,"addic");
1099       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
1100       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1101    
1102       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
1103    
1104       iop = ppc32_op_emit_insn_output(cpu,1,"addic");
1105    
1106       if (rd != ra)
1107          x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_ra,4);
1108    
1109     ppc32_load_imm(b,X86_EAX,tmp);     x86_alu_reg_imm(iop->ob_ptr,X86_ADD,hreg_rd,tmp);
1110     ppc32_alu_gpr(b,X86_ADD,X86_EAX,ra);     ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
1111     ppc32_store_gpr(b,rd,X86_EAX);  
1112     x86_set_membase(b->jit_ptr,X86_CC_C,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),FALSE);     x86_set_membase(iop->ob_ptr,X86_CC_C,
1113                       X86_EDI,OFFSET(cpu_ppc_t,xer_ca),FALSE);
1114    
1115       ppc32_jit_close_hreg_seq(cpu);
1116     return(0);     return(0);
1117  }  }
1118    
# Line 657  DECLARE_INSN(ADDIC_dot) Line 1123  DECLARE_INSN(ADDIC_dot)
1123     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1124     int imm = bits(insn,0,15);     int imm = bits(insn,0,15);
1125     m_uint32_t tmp = sign_extend_32(imm,16);     m_uint32_t tmp = sign_extend_32(imm,16);
1126       int hreg_rd,hreg_ra;
1127       jit_op_t *iop;
1128    
1129       /* $rd = $ra + imm */
1130       ppc32_jit_start_hreg_seq(cpu,"addic.");
1131       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
1132       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1133    
1134       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
1135    
1136     ppc32_load_imm(b,X86_EAX,tmp);     iop = ppc32_op_emit_insn_output(cpu,1,"addic.");
    ppc32_alu_gpr(b,X86_ADD,X86_EAX,ra);  
    ppc32_store_gpr(b,rd,X86_EAX);  
    x86_set_membase(b->jit_ptr,X86_CC_C,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),FALSE);  
1137    
1138     x86_test_reg_reg(b->jit_ptr,X86_EAX,X86_EAX);     if (rd != ra)
1139     ppc32_update_cr0(b);        x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_ra,4);
1140    
1141       x86_alu_reg_imm(iop->ob_ptr,X86_ADD,hreg_rd,tmp);
1142       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
1143    
1144       x86_set_membase(iop->ob_ptr,X86_CC_C,
1145                       X86_EDI,OFFSET(cpu_ppc_t,xer_ca),FALSE);
1146    
1147       ppc32_op_emit_update_flags(cpu,0,TRUE);
1148    
1149       ppc32_jit_close_hreg_seq(cpu);
1150     return(0);     return(0);
1151  }  }
1152    
# Line 674  DECLARE_INSN(ADDIS) Line 1156  DECLARE_INSN(ADDIS)
1156     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
1157     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1158     m_uint32_t imm = bits(insn,0,15);     m_uint32_t imm = bits(insn,0,15);
1159       m_uint32_t tmp = imm << 16;
1160       int hreg_rd,hreg_ra;
1161       jit_op_t *iop;
1162    
1163       /* $rd = $ra + (imm << 16) */
1164       ppc32_jit_start_hreg_seq(cpu,"addis");
1165       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
1166    
1167       if (ra != 0) {
1168          hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1169          ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
1170    
1171          iop = ppc32_op_emit_insn_output(cpu,1,"addis");
1172    
1173          if (rd != ra)
1174             x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_ra,4);
1175    
1176          x86_alu_reg_imm(iop->ob_ptr,X86_ADD,hreg_rd,tmp);
1177       } else {
1178          //iop = ppc32_op_emit_insn_output(cpu,1,"addis");
1179          //x86_mov_reg_imm(iop->ob_ptr,hreg_rd,tmp);
1180          ppc32_op_emit_set_host_reg_imm32(cpu,hreg_rd,tmp);
1181       }
1182    
1183       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
1184    
1185       ppc32_jit_close_hreg_seq(cpu);
1186       return(0);
1187    }
1188    
1189    /* ADDZE */
1190    DECLARE_INSN(ADDZE)
1191    {
1192       int rd = bits(insn,21,25);
1193       int ra = bits(insn,16,20);
1194       int hreg_rd,hreg_ra,hreg_t0;
1195       jit_op_t *iop;
1196    
1197       /* $rd = $ra + xer_ca + set_carry */
1198       ppc32_jit_start_hreg_seq(cpu,"addze");
1199       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
1200       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1201       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
1202    
1203       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
1204    
1205       iop = ppc32_op_emit_insn_output(cpu,2,"addze");
1206    
1207       x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_t0,hreg_t0);
1208    
1209       if (rd != ra)
1210          x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_ra,4);
1211    
1212       x86_alu_reg_membase(iop->ob_ptr,X86_ADD,hreg_rd,
1213                           X86_EDI,OFFSET(cpu_ppc_t,xer_ca));
1214    
1215     ppc32_load_imm(b,X86_EBX,imm << 16);     x86_set_reg(iop->ob_ptr,X86_CC_C,hreg_t0,FALSE);
1216       x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),hreg_t0,4);
1217    
1218     if (ra != 0)     ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
       x86_alu_reg_membase(b->jit_ptr,X86_ADD,X86_EBX,X86_EDI,REG_OFFSET(ra));  
1219    
1220     ppc32_store_gpr(b,rd,X86_EBX);     if (insn & 1)
1221          ppc32_op_emit_update_flags(cpu,0,TRUE);
1222    
1223       ppc32_jit_close_hreg_seq(cpu);
1224     return(0);     return(0);
1225  }  }
1226    
# Line 690  DECLARE_INSN(AND) Line 1230  DECLARE_INSN(AND)
1230     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
1231     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1232     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
1233       int hreg_rs,hreg_ra,hreg_rb;
1234       jit_op_t *iop;
1235    
1236     ppc32_load_gpr(b,X86_EBX,rs);     /* $ra = $rs & $rb */
1237     ppc32_alu_gpr(b,X86_AND,X86_EBX,rb);     ppc32_jit_start_hreg_seq(cpu,"and");
1238     ppc32_store_gpr(b,ra,X86_EBX);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
1239       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1240       hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
1241    
1242       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
1243       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
1244    
1245       iop = ppc32_op_emit_insn_output(cpu,1,"and");
1246    
1247       if (ra == rs)
1248          x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_ra,hreg_rb);
1249       else if (ra == rb)
1250          x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_ra,hreg_rs);
1251       else {
1252          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
1253          x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_ra,hreg_rb);
1254       }
1255    
1256       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
1257    
1258     if (insn & 1)     if (insn & 1)
1259        ppc32_update_cr0(b);        ppc32_op_emit_update_flags(cpu,0,TRUE);
1260    
1261       ppc32_jit_close_hreg_seq(cpu);
1262     return(0);     return(0);
1263  }  }
1264    
# Line 707  DECLARE_INSN(ANDC) Line 1268  DECLARE_INSN(ANDC)
1268     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
1269     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1270     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
1271       int hreg_rs,hreg_ra,hreg_rb,hreg_t0;
1272       jit_op_t *iop;
1273    
1274     /* $ra = $rs & ~$rb */     /* $ra = $rs & ~$rb */
1275     ppc32_load_gpr(b,X86_EBX,rb);     ppc32_jit_start_hreg_seq(cpu,"andc");
1276     x86_not_reg(b->jit_ptr,X86_EBX);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
1277     ppc32_alu_gpr(b,X86_AND,X86_EBX,rs);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1278     ppc32_store_gpr(b,ra,X86_EBX);     hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
1279    
1280       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
1281       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
1282    
1283       iop = ppc32_op_emit_insn_output(cpu,1,"andc");
1284    
1285       /* $t0 = ~$rb */
1286       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
1287       x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_rb,4);
1288       x86_not_reg(iop->ob_ptr,hreg_t0);
1289    
1290       /* $ra = $rs & $t0 */
1291       if (ra == rs)
1292          x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_ra,hreg_t0);
1293       else {
1294          x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_t0,hreg_rs);
1295          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_t0,4);
1296       }
1297    
1298       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
1299    
1300     if (insn & 1)     if (insn & 1)
1301        ppc32_update_cr0(b);        ppc32_op_emit_update_flags(cpu,0,TRUE);
1302    
1303       ppc32_jit_close_hreg_seq(cpu);
1304     return(0);     return(0);
1305  }  }
1306    
# Line 726  DECLARE_INSN(ANDI) Line 1310  DECLARE_INSN(ANDI)
1310     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
1311     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1312     m_uint16_t imm = bits(insn,0,15);     m_uint16_t imm = bits(insn,0,15);
1313       m_uint32_t tmp = imm;
1314       int hreg_rs,hreg_ra;
1315       jit_op_t *iop;
1316    
1317     /* $ra = $rs & imm */     /* $ra = $rs & imm */
1318     ppc32_load_imm(b,X86_EBX,imm);     ppc32_jit_start_hreg_seq(cpu,"andi");
1319     ppc32_alu_gpr(b,X86_AND,X86_EBX,rs);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
1320     ppc32_store_gpr(b,ra,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1321    
1322       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
1323    
1324     ppc32_update_cr0(b);     iop = ppc32_op_emit_insn_output(cpu,2,"andi");
1325    
1326       if (ra != rs)
1327          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
1328    
1329       x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_ra,tmp);
1330       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
1331    
1332       ppc32_op_emit_update_flags(cpu,0,TRUE);
1333    
1334       ppc32_jit_close_hreg_seq(cpu);
1335     return(0);     return(0);
1336  }  }
1337    
# Line 742  DECLARE_INSN(ANDIS) Line 1341  DECLARE_INSN(ANDIS)
1341     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
1342     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1343     m_uint32_t imm = bits(insn,0,15);     m_uint32_t imm = bits(insn,0,15);
1344       m_uint32_t tmp = imm << 16;
1345       int hreg_rs,hreg_ra;
1346       jit_op_t *iop;
1347    
1348     /* $ra = $rs & imm */     /* $ra = $rs & imm */
1349     ppc32_load_imm(b,X86_EBX,imm << 16);     ppc32_jit_start_hreg_seq(cpu,"andis");
1350     ppc32_alu_gpr(b,X86_AND,X86_EBX,rs);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
1351     ppc32_store_gpr(b,ra,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1352    
1353       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
1354    
1355       iop = ppc32_op_emit_insn_output(cpu,2,"andis");
1356    
1357       if (ra != rs)
1358          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
1359    
1360       x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_ra,tmp);
1361       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
1362    
1363       ppc32_op_emit_update_flags(cpu,0,TRUE);
1364    
1365     ppc32_update_cr0(b);     ppc32_jit_close_hreg_seq(cpu);
1366     return(0);     return(0);
1367  }  }
1368    
# Line 756  DECLARE_INSN(ANDIS) Line 1370  DECLARE_INSN(ANDIS)
1370  DECLARE_INSN(B)  DECLARE_INSN(B)
1371  {  {
1372     m_uint32_t offset = bits(insn,2,25);     m_uint32_t offset = bits(insn,2,25);
1373     m_uint64_t new_ia;     m_uint32_t new_ia;
1374       jit_op_t *iop;
1375    
1376       iop = ppc32_op_emit_insn_output(cpu,4,"b");
1377    
1378     /* compute the new ia */     /* compute the new ia */
1379     new_ia = b->start_ia + ((b->ppc_trans_pos-1) << 2);     new_ia = b->start_ia + (b->ppc_trans_pos << 2);
1380     new_ia += sign_extend(offset << 2,26);     new_ia += sign_extend(offset << 2,26);
1381     ppc32_set_jump(cpu,b,new_ia,1);     ppc32_set_jump(cpu,b,iop,new_ia,TRUE);
1382    
1383       ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
1384       ppc32_op_emit_branch_target(cpu,b,new_ia);
1385       ppc32_op_emit_branch_target(cpu,b,b->start_ia+((b->ppc_trans_pos+1) << 2));
1386     return(0);     return(0);
1387  }  }
1388    
# Line 769  DECLARE_INSN(B) Line 1390  DECLARE_INSN(B)
1390  DECLARE_INSN(BA)  DECLARE_INSN(BA)
1391  {  {
1392     m_uint32_t offset = bits(insn,2,25);     m_uint32_t offset = bits(insn,2,25);
1393     m_uint64_t new_ia;     m_uint32_t new_ia;
1394       jit_op_t *iop;
1395    
1396       iop = ppc32_op_emit_insn_output(cpu,4,"ba");
1397    
1398     /* compute the new ia */     /* compute the new ia */
1399     new_ia = sign_extend(offset << 2,26);     new_ia = sign_extend(offset << 2,26);
1400     ppc32_set_jump(cpu,b,new_ia,1);     ppc32_set_jump(cpu,b,iop,new_ia,TRUE);
1401    
1402       ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
1403       ppc32_op_emit_branch_target(cpu,b,new_ia);
1404       ppc32_op_emit_branch_target(cpu,b,b->start_ia+((b->ppc_trans_pos+1) << 2));
1405     return(0);     return(0);
1406  }  }
1407    
# Line 781  DECLARE_INSN(BA) Line 1409  DECLARE_INSN(BA)
1409  DECLARE_INSN(BL)  DECLARE_INSN(BL)
1410  {  {
1411     m_uint32_t offset = bits(insn,2,25);     m_uint32_t offset = bits(insn,2,25);
1412     m_uint64_t new_ia;     m_uint32_t new_ia;
1413       jit_op_t *iop;
1414    
1415       iop = ppc32_op_emit_insn_output(cpu,4,"bl");
1416    
1417     /* compute the new ia */     /* compute the new ia */
1418     new_ia = b->start_ia + ((b->ppc_trans_pos-1) << 2);     new_ia = b->start_ia + (b->ppc_trans_pos << 2);
1419     new_ia += sign_extend(offset << 2,26);     new_ia += sign_extend(offset << 2,26);
1420    
1421     /* set the return address */     /* set the return address */
1422     ppc32_set_lr(b,b->start_ia + (b->ppc_trans_pos << 2));     ppc32_set_lr(iop,b->start_ia + ((b->ppc_trans_pos+1) << 2));
1423       ppc32_set_jump(cpu,b,iop,new_ia,TRUE);
1424    
1425     ppc32_set_jump(cpu,b,new_ia,1);     ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
1426       ppc32_op_emit_branch_target(cpu,b,new_ia);
1427       ppc32_op_emit_branch_target(cpu,b,b->start_ia+((b->ppc_trans_pos+1) << 2));
1428     return(0);     return(0);
1429  }  }
1430    
# Line 798  DECLARE_INSN(BL) Line 1432  DECLARE_INSN(BL)
1432  DECLARE_INSN(BLA)  DECLARE_INSN(BLA)
1433  {  {
1434     m_uint32_t offset = bits(insn,2,25);     m_uint32_t offset = bits(insn,2,25);
1435     m_uint64_t new_ia;     m_uint32_t new_ia;
1436       jit_op_t *iop;
1437    
1438       iop = ppc32_op_emit_insn_output(cpu,4,"bla");
1439    
1440     /* compute the new ia */     /* compute the new ia */
1441     new_ia = sign_extend(offset << 2,26);     new_ia = sign_extend(offset << 2,26);
1442    
1443     /* set the return address */     /* set the return address */
1444     ppc32_set_lr(b,b->start_ia + (b->ppc_trans_pos << 2));     ppc32_set_lr(iop,b->start_ia + ((b->ppc_trans_pos+1) << 2));
1445       ppc32_set_jump(cpu,b,iop,new_ia,TRUE);
1446    
1447     ppc32_set_jump(cpu,b,new_ia,1);     ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
1448       ppc32_op_emit_branch_target(cpu,b,new_ia);
1449       ppc32_op_emit_branch_target(cpu,b,b->start_ia+((b->ppc_trans_pos+1) << 2));
1450     return(0);     return(0);
1451  }  }
1452    
# Line 816  DECLARE_INSN(BCC) Line 1456  DECLARE_INSN(BCC)
1456     int bo = bits(insn,21,25);     int bo = bits(insn,21,25);
1457     int bi = bits(insn,16,20);     int bi = bits(insn,16,20);
1458     int bd = bits(insn,2,15);     int bd = bits(insn,2,15);
1459       jit_op_t *iop;
1460       u_int cr_field,cr_bit;
1461     m_uint32_t new_ia;     m_uint32_t new_ia;
1462     u_char *jump_ptr;     u_char *jump_ptr;
1463     int local_jump;     int local_jump;
1464     int cond;     int cond;
1465    
1466       ppc32_op_emit_basic_opcode(cpu,JIT_OP_BRANCH_JUMP);
1467    
1468       iop = ppc32_op_emit_insn_output(cpu,5,"bcc");
1469    
1470     /* Get the wanted value for the condition bit */     /* Get the wanted value for the condition bit */
1471     cond = (bo >> 3) & 0x1;     cond = (bo >> 3) & 0x1;
1472    
1473     /* Set the return address */     /* Set the return address */
1474     if (insn & 1)     if (insn & 1) {
1475        ppc32_set_lr(b,b->start_ia + (b->ppc_trans_pos << 2));        ppc32_set_lr(iop,b->start_ia + ((b->ppc_trans_pos+1) << 2));
1476          ppc32_op_emit_branch_target(cpu,b,b->start_ia+((b->ppc_trans_pos+1)<<2));
1477       }
1478    
1479     /* Compute the new ia */     /* Compute the new ia */
1480     new_ia = sign_extend_32(bd << 2,16);     new_ia = sign_extend_32(bd << 2,16);
1481     if (!(insn & 0x02))     if (!(insn & 0x02))
1482        new_ia += b->start_ia + ((b->ppc_trans_pos-1) << 2);        new_ia += b->start_ia + (b->ppc_trans_pos << 2);
1483    
1484     /* Test the condition bit */     /* Test the condition bit */
1485     x86_test_membase_imm(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,cr),     cr_field = ppc32_get_cr_field(bi);
1486                          (1 << (31 - bi)));     cr_bit = ppc32_get_cr_bit(bi);
1487    
1488       ppc32_op_emit_require_flags(cpu,cr_field);
1489    
1490       x86_test_membase_imm(iop->ob_ptr,
1491                            X86_EDI,PPC32_CR_FIELD_OFFSET(cr_field),
1492                            (1 << cr_bit));
1493    
1494     local_jump = ppc32_jit_tcb_local_addr(b,new_ia,&jump_ptr);     local_jump = ppc32_jit_tcb_local_addr(b,new_ia,&jump_ptr);
1495    
# Line 844  DECLARE_INSN(BCC) Line 1498  DECLARE_INSN(BCC)
1498      * page or not.      * page or not.
1499      */      */
1500     if (local_jump) {     if (local_jump) {
1501        if (jump_ptr) {        ppc32_jit_tcb_record_patch(b,iop,iop->ob_ptr,new_ia);
1502           x86_branch(b->jit_ptr,(cond) ? X86_CC_NZ : X86_CC_Z,jump_ptr,FALSE);        x86_branch32(iop->ob_ptr,(cond) ? X86_CC_NZ : X86_CC_Z,0,FALSE);
       } else {  
          ppc32_jit_tcb_record_patch(b,b->jit_ptr,new_ia);  
          x86_branch32(b->jit_ptr,(cond) ? X86_CC_NZ : X86_CC_Z,0,FALSE);  
       }  
1503     } else {       } else {  
1504        jump_ptr = b->jit_ptr;        jump_ptr = iop->ob_ptr;
1505        x86_branch32(b->jit_ptr,(cond) ? X86_CC_Z : X86_CC_NZ,0,FALSE);        x86_branch32(iop->ob_ptr,(cond) ? X86_CC_Z : X86_CC_NZ,0,FALSE);
1506        ppc32_set_jump(cpu,b,new_ia,TRUE);        ppc32_set_jump(cpu,b,iop,new_ia,TRUE);
1507        x86_patch(jump_ptr,b->jit_ptr);        x86_patch(jump_ptr,iop->ob_ptr);
1508     }     }
1509    
1510       ppc32_op_emit_branch_target(cpu,b,new_ia);
1511     return(0);     return(0);
1512  }  }
1513    
# Line 866  DECLARE_INSN(BC) Line 1517  DECLARE_INSN(BC)
1517     int bo = bits(insn,21,25);     int bo = bits(insn,21,25);
1518     int bi = bits(insn,16,20);     int bi = bits(insn,16,20);
1519     int bd = bits(insn,2,15);     int bd = bits(insn,2,15);
1520       int hreg_t0,hreg_t1;
1521       jit_op_t *iop;
1522       u_int cr_field,cr_bit;
1523     m_uint32_t new_ia;     m_uint32_t new_ia;
1524     u_char *jump_ptr;     u_char *jump_ptr;
1525     int local_jump;     int local_jump;
1526     int cond,ctr;     int cond,ctr;
1527    
1528       ppc32_op_emit_basic_opcode(cpu,JIT_OP_BRANCH_JUMP);
1529    
1530       iop = ppc32_op_emit_insn_output(cpu,5,"bc");
1531    
1532       ppc32_jit_start_hreg_seq(cpu,"bc");
1533       hreg_t0 = ppc32_jit_alloc_hreg(cpu,-1);
1534       hreg_t1 = ppc32_jit_get_tmp_hreg(cpu);
1535    
1536       ppc32_op_emit_alter_host_reg(cpu,hreg_t0);
1537    
1538     /* Get the wanted value for the condition bit and CTR value */     /* Get the wanted value for the condition bit and CTR value */
1539     cond = (bo >> 3) & 0x1;     cond = (bo >> 3) & 0x1;
1540     ctr  = (bo >> 1) & 0x1;     ctr  = (bo >> 1) & 0x1;
1541    
1542     /* Set the return address */     /* Set the return address */
1543     if (insn & 1)     if (insn & 1) {
1544        ppc32_set_lr(b,b->start_ia + (b->ppc_trans_pos << 2));        ppc32_set_lr(iop,b->start_ia + ((b->ppc_trans_pos+1) << 2));
1545          ppc32_op_emit_branch_target(cpu,b,b->start_ia+((b->ppc_trans_pos+1)<<2));
1546       }
1547    
1548     /* Compute the new ia */     /* Compute the new ia */
1549     new_ia = sign_extend_32(bd << 2,16);     new_ia = sign_extend_32(bd << 2,16);
1550     if (!(insn & 0x02))     if (!(insn & 0x02))
1551        new_ia += b->start_ia + ((b->ppc_trans_pos-1) << 2);        new_ia += b->start_ia + (b->ppc_trans_pos << 2);
1552    
1553     x86_mov_reg_imm(b->jit_ptr,X86_EAX,1);     x86_mov_reg_imm(iop->ob_ptr,hreg_t0,1);
1554    
1555     /* Decrement the count register */     /* Decrement the count register */
1556     if (!(bo & 0x04)) {     if (!(bo & 0x04)) {
1557        x86_dec_membase(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,ctr));        x86_dec_membase(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,ctr));
1558        x86_set_reg(b->jit_ptr,(ctr) ? X86_CC_Z : X86_CC_NZ,X86_EBX,FALSE);        x86_set_reg(iop->ob_ptr,(ctr) ? X86_CC_Z : X86_CC_NZ,hreg_t1,FALSE);
1559        x86_alu_reg_reg(b->jit_ptr,X86_AND,X86_EAX,X86_EBX);        x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_t0,hreg_t1);
1560     }     }
1561    
1562     /* Test the condition bit */     /* Test the condition bit */
1563     if (!((bo >> 4) & 0x01)) {     if (!((bo >> 4) & 0x01)) {
1564        x86_test_membase_imm(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,cr),        cr_field = ppc32_get_cr_field(bi);
1565                             (1 << (31 - bi)));        cr_bit = ppc32_get_cr_bit(bi);
1566        x86_set_reg(b->jit_ptr,(cond) ? X86_CC_NZ : X86_CC_Z,X86_ECX,FALSE);  
1567        x86_alu_reg_reg(b->jit_ptr,X86_AND,X86_EAX,X86_ECX);        ppc32_op_emit_require_flags(cpu,cr_field);
1568    
1569          x86_test_membase_imm(iop->ob_ptr,
1570                               X86_EDI,PPC32_CR_FIELD_OFFSET(cr_field),
1571                               (1 << cr_bit));
1572    
1573          x86_set_reg(iop->ob_ptr,(cond) ? X86_CC_NZ : X86_CC_Z,hreg_t1,FALSE);
1574          x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_t0,hreg_t1);
1575     }     }
1576    
1577     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,0x01);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x01);
1578    
1579     local_jump = ppc32_jit_tcb_local_addr(b,new_ia,&jump_ptr);     local_jump = ppc32_jit_tcb_local_addr(b,new_ia,&jump_ptr);
1580    
# Line 910  DECLARE_INSN(BC) Line 1583  DECLARE_INSN(BC)
1583      * page or not.      * page or not.
1584      */      */
1585     if (local_jump) {     if (local_jump) {
1586        if (jump_ptr) {        ppc32_jit_tcb_record_patch(b,iop,iop->ob_ptr,new_ia);
1587           x86_branch(b->jit_ptr,X86_CC_NZ,jump_ptr,FALSE);        x86_branch32(iop->ob_ptr,X86_CC_NZ,0,FALSE);
       } else {  
          ppc32_jit_tcb_record_patch(b,b->jit_ptr,new_ia);  
          x86_branch32(b->jit_ptr,X86_CC_NZ,0,FALSE);  
       }  
1588     } else {       } else {  
1589        jump_ptr = b->jit_ptr;        jump_ptr = iop->ob_ptr;
1590        x86_branch32(b->jit_ptr,X86_CC_Z,0,FALSE);        x86_branch32(iop->ob_ptr,X86_CC_Z,0,FALSE);
1591        ppc32_set_jump(cpu,b,new_ia,TRUE);        ppc32_set_jump(cpu,b,iop,new_ia,TRUE);
1592        x86_patch(jump_ptr,b->jit_ptr);        x86_patch(jump_ptr,iop->ob_ptr);
1593     }     }
1594    
1595       ppc32_op_emit_branch_target(cpu,b,new_ia);
1596    
1597       ppc32_jit_close_hreg_seq(cpu);
1598     return(0);     return(0);
1599  }  }
1600    
# Line 932  DECLARE_INSN(BCLR) Line 1604  DECLARE_INSN(BCLR)
1604     int bo = bits(insn,21,25);     int bo = bits(insn,21,25);
1605     int bi = bits(insn,16,20);     int bi = bits(insn,16,20);
1606     int bd = bits(insn,2,15);     int bd = bits(insn,2,15);
1607       int hreg_t0,hreg_t1;
1608       jit_op_t *iop;
1609       u_int cr_field,cr_bit;
1610     m_uint32_t new_ia;     m_uint32_t new_ia;
1611     u_char *jump_ptr;     u_char *jump_ptr;
1612     int cond,ctr;     int cond,ctr;
1613    
1614       ppc32_jit_start_hreg_seq(cpu,"bclr");
1615       hreg_t0 = ppc32_jit_alloc_hreg(cpu,-1);
1616       hreg_t1 = ppc32_jit_get_tmp_hreg(cpu);
1617    
1618       ppc32_op_emit_alter_host_reg(cpu,hreg_t0);
1619    
1620       iop = ppc32_op_emit_insn_output(cpu,5,"bclr");
1621    
1622     /* Get the wanted value for the condition bit and CTR value */     /* Get the wanted value for the condition bit and CTR value */
1623     cond = (bo >> 3) & 0x1;     cond = (bo >> 3) & 0x1;
1624     ctr  = (bo >> 1) & 0x1;     ctr  = (bo >> 1) & 0x1;
# Line 943  DECLARE_INSN(BCLR) Line 1626  DECLARE_INSN(BCLR)
1626     /* Compute the new ia */     /* Compute the new ia */
1627     new_ia = sign_extend_32(bd << 2,16);     new_ia = sign_extend_32(bd << 2,16);
1628     if (!(insn & 0x02))     if (!(insn & 0x02))
1629        new_ia += b->start_ia + ((b->ppc_trans_pos-1) << 2);        new_ia += b->start_ia + (b->ppc_trans_pos << 2);
1630    
1631     ppc32_load_imm(b,X86_EAX,1);     x86_mov_reg_imm(iop->ob_ptr,hreg_t0,1);
1632    
1633     /* Decrement the count register */     /* Decrement the count register */
1634     if (!(bo & 0x04)) {     if (!(bo & 0x04)) {
1635        x86_dec_membase(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,ctr));        x86_dec_membase(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,ctr));
1636        x86_set_reg(b->jit_ptr,(ctr) ? X86_CC_Z : X86_CC_NZ,X86_EBX,FALSE);        x86_set_reg(iop->ob_ptr,(ctr) ? X86_CC_Z : X86_CC_NZ,hreg_t1,FALSE);
1637        x86_alu_reg_reg(b->jit_ptr,X86_AND,X86_EAX,X86_EBX);        x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_t0,hreg_t1);
1638     }     }
1639    
1640     /* Test the condition bit */     /* Test the condition bit */
1641     if (!((bo >> 4) & 0x01)) {     if (!((bo >> 4) & 0x01)) {
1642        x86_test_membase_imm(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,cr),        cr_field = ppc32_get_cr_field(bi);
1643                             (1 << (31 - bi)));        cr_bit = ppc32_get_cr_bit(bi);
1644        x86_set_reg(b->jit_ptr,(cond) ? X86_CC_NZ : X86_CC_Z,X86_ECX,FALSE);  
1645        x86_alu_reg_reg(b->jit_ptr,X86_AND,X86_EAX,X86_ECX);        ppc32_op_emit_require_flags(cpu,cr_field);
1646    
1647          x86_test_membase_imm(iop->ob_ptr,
1648                               X86_EDI,PPC32_CR_FIELD_OFFSET(cr_field),
1649                               (1 << cr_bit));
1650    
1651          x86_set_reg(iop->ob_ptr,(cond) ? X86_CC_NZ : X86_CC_Z,hreg_t1,FALSE);
1652          x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_t0,hreg_t1);
1653     }     }
1654    
1655     /* Set the return address */     /* Set the return address */
1656     x86_mov_reg_membase(b->jit_ptr,X86_EDX,X86_EDI,OFFSET(cpu_ppc_t,lr),4);     x86_mov_reg_membase(iop->ob_ptr,hreg_t1,X86_EDI,OFFSET(cpu_ppc_t,lr),4);
1657    
1658     if (insn & 1)     if (insn & 1) {
1659        ppc32_set_lr(b,b->start_ia + (b->ppc_trans_pos << 2));        ppc32_set_lr(iop,b->start_ia + ((b->ppc_trans_pos+1) << 2));
1660          ppc32_op_emit_branch_target(cpu,b,b->start_ia+((b->ppc_trans_pos+1)<<2));
1661       }
1662    
1663     /* Branching */     /* Branching */
1664     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,0x01);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x01);
1665    
1666       jump_ptr = iop->ob_ptr;
1667       x86_branch32(iop->ob_ptr,X86_CC_Z,0,FALSE);
1668    
1669       x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t1,0xFFFFFFFC);
1670       x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,ia),hreg_t1,4);
1671       ppc32_jit_tcb_push_epilog(&iop->ob_ptr);
1672    
1673     jump_ptr = b->jit_ptr;     x86_patch(jump_ptr,iop->ob_ptr);
    x86_branch32(b->jit_ptr,X86_CC_Z,0,FALSE);  
1674    
1675     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EDX,0xFFFFFFFC);     ppc32_op_emit_basic_opcode(cpu,JIT_OP_EOB);
    x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,ia),X86_EDX,4);  
    ppc32_jit_tcb_push_epilog(b);  
1676    
1677     x86_patch(jump_ptr,b->jit_ptr);     ppc32_jit_close_hreg_seq(cpu);
1678     return(0);     return(0);
1679  }  }
1680    
# Line 988  DECLARE_INSN(CMP) Line 1684  DECLARE_INSN(CMP)
1684     int rd = bits(insn,23,25);     int rd = bits(insn,23,25);
1685     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1686     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
1687       int hreg_ra,hreg_rb;
1688       jit_op_t *iop;
1689      
1690       ppc32_jit_start_hreg_seq(cpu,"cmp");
1691       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1692       hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
1693    
1694       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
1695       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
1696    
1697       iop = ppc32_op_emit_insn_output(cpu,1,"cmp");
1698    
1699     ppc32_load_gpr(b,X86_EBX,ra);     x86_alu_reg_reg(iop->ob_ptr,X86_CMP,hreg_ra,hreg_rb);
1700     ppc32_alu_gpr(b,X86_CMP,X86_EBX,rb);     ppc32_op_emit_update_flags(cpu,rd,TRUE);
1701     ppc32_update_cr(b,rd,TRUE);  
1702       ppc32_jit_close_hreg_seq(cpu);
1703     return(0);     return(0);
1704  }  }
1705    
# Line 1002  DECLARE_INSN(CMPI) Line 1710  DECLARE_INSN(CMPI)
1710     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1711     m_uint16_t imm = bits(insn,0,15);     m_uint16_t imm = bits(insn,0,15);
1712     m_uint32_t tmp = sign_extend_32(imm,16);     m_uint32_t tmp = sign_extend_32(imm,16);
1713       int hreg_ra;
1714       jit_op_t *iop;
1715    
1716       ppc32_jit_start_hreg_seq(cpu,"cmpi");
1717       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1718       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
1719    
1720     ppc32_load_imm(b,X86_EBX,tmp);     iop = ppc32_op_emit_insn_output(cpu,1,"cmpi");
    ppc32_load_gpr(b,X86_ESI,ra);  
    x86_alu_reg_reg(b->jit_ptr,X86_CMP,X86_ESI,X86_EBX);  
1721    
1722     ppc32_update_cr(b,rd,TRUE);     x86_alu_reg_imm(iop->ob_ptr,X86_CMP,hreg_ra,tmp);
1723       ppc32_op_emit_update_flags(cpu,rd,TRUE);
1724    
1725       ppc32_jit_close_hreg_seq(cpu);
1726     return(0);     return(0);
1727  }  }
1728    
# Line 1017  DECLARE_INSN(CMPL) Line 1732  DECLARE_INSN(CMPL)
1732     int rd = bits(insn,23,25);     int rd = bits(insn,23,25);
1733     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1734     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
1735       int hreg_ra,hreg_rb;
1736       jit_op_t *iop;
1737      
1738       ppc32_jit_start_hreg_seq(cpu,"cmpl");
1739       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1740       hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
1741    
1742       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
1743       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
1744    
1745       iop = ppc32_op_emit_insn_output(cpu,1,"cmpl");
1746    
1747     ppc32_load_gpr(b,X86_EAX,ra);     x86_alu_reg_reg(iop->ob_ptr,X86_CMP,hreg_ra,hreg_rb);
1748     ppc32_alu_gpr(b,X86_CMP,X86_EAX,rb);     ppc32_op_emit_update_flags(cpu,rd,FALSE);
1749     ppc32_update_cr(b,rd,FALSE);  
1750       ppc32_jit_close_hreg_seq(cpu);
1751     return(0);     return(0);
1752  }  }
1753    
# Line 1029  DECLARE_INSN(CMPLI) Line 1756  DECLARE_INSN(CMPLI)
1756  {  {
1757     int rd = bits(insn,23,25);     int rd = bits(insn,23,25);
1758     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
1759     m_uint16_t imm = bits(insn,0,15);     m_uint32_t imm = bits(insn,0,15);
1760       int hreg_ra;
1761       jit_op_t *iop;
1762    
1763       ppc32_jit_start_hreg_seq(cpu,"cmpli");
1764       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
1765       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
1766    
1767       iop = ppc32_op_emit_insn_output(cpu,1,"cmpli");
1768    
1769     ppc32_load_imm(b,X86_EBX,imm);     x86_alu_reg_imm(iop->ob_ptr,X86_CMP,hreg_ra,imm);
1770     ppc32_load_gpr(b,X86_ESI,ra);     ppc32_op_emit_update_flags(cpu,rd,FALSE);
    x86_alu_reg_reg(b->jit_ptr,X86_CMP,X86_ESI,X86_EBX);  
1771    
1772     ppc32_update_cr(b,rd,FALSE);     ppc32_jit_close_hreg_seq(cpu);
1773     return(0);     return(0);
1774  }  }
1775    
# Line 1045  DECLARE_INSN(CRAND) Line 1779  DECLARE_INSN(CRAND)
1779     int bd = bits(insn,21,25);     int bd = bits(insn,21,25);
1780     int bb = bits(insn,16,20);     int bb = bits(insn,16,20);
1781     int ba = bits(insn,11,15);     int ba = bits(insn,11,15);
1782       int hreg_t0;
1783       jit_op_t *iop;
1784    
1785     ppc32_load_cr(b,X86_ESI);     ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
1786    
1787       ppc32_jit_start_hreg_seq(cpu,"crand");
1788       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
1789       ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
1790    
1791       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(ba));
1792       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bb));
1793       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bd));
1794    
1795       iop = ppc32_op_emit_insn_output(cpu,3,"crand");
1796    
1797     /* test $ba bit */     /* test $ba bit */
1798     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - ba)));     x86_test_membase_imm(iop->ob_ptr,
1799     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EAX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(ba)),
1800                            (1 << ppc32_get_cr_bit(ba)));
1801       x86_set_reg(iop->ob_ptr,X86_CC_NZ,X86_EDX,FALSE);
1802    
1803     /* test $bb bit */     /* test $bb bit */
1804     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - bb)));     x86_test_membase_imm(iop->ob_ptr,
1805     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EBX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bb)),
1806                            (1 << ppc32_get_cr_bit(bb)));
1807       x86_set_reg(iop->ob_ptr,X86_CC_NZ,hreg_t0,FALSE);
1808        
1809     /* result of AND between $ba and $bb */     /* result of AND between $ba and $bb */
1810     x86_alu_reg_reg(b->jit_ptr,X86_AND,X86_EBX,X86_EAX);     x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_t0,X86_EDX);
1811     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,0x01);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x01);
1812        
1813     /* set/clear $bd bit depending on the result */     /* set/clear $bd bit depending on the result */
1814     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,~(1 << (31 - bd)));     x86_alu_membase_imm(iop->ob_ptr,X86_AND,
1815     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,(31 - bd));                         X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
1816     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_ESI,X86_EBX);                         ~(1 << ppc32_get_cr_bit(bd)));
1817    
1818       x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_t0,ppc32_get_cr_bit(bd));
1819       x86_alu_membase_reg(iop->ob_ptr,X86_OR,
1820                           X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
1821                           hreg_t0);
1822    
1823     ppc32_store_cr(b,X86_ESI);     ppc32_jit_close_hreg_seq(cpu);
1824     return(0);     return(0);
1825  }  }
1826    
# Line 1075  DECLARE_INSN(CRANDC) Line 1830  DECLARE_INSN(CRANDC)
1830     int bd = bits(insn,21,25);     int bd = bits(insn,21,25);
1831     int bb = bits(insn,16,20);     int bb = bits(insn,16,20);
1832     int ba = bits(insn,11,15);     int ba = bits(insn,11,15);
1833       int hreg_t0;
1834       jit_op_t *iop;
1835    
1836       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
1837    
1838     ppc32_load_cr(b,X86_ESI);     ppc32_jit_start_hreg_seq(cpu,"crandc");
1839       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
1840       ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
1841    
1842       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(ba));
1843       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bb));
1844       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bd));
1845    
1846       iop = ppc32_op_emit_insn_output(cpu,3,"crandc");
1847    
1848     /* test $ba bit */     /* test $ba bit */
1849     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - ba)));     x86_test_membase_imm(iop->ob_ptr,
1850     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EAX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(ba)),
1851                            (1 << ppc32_get_cr_bit(ba)));
1852       x86_set_reg(iop->ob_ptr,X86_CC_NZ,X86_EDX,FALSE);
1853    
1854     /* test $bb bit */     /* test $bb bit */
1855     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - bb)));     x86_test_membase_imm(iop->ob_ptr,
1856     x86_set_reg(b->jit_ptr,X86_CC_Z,X86_EBX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bb)),
1857                            (1 << ppc32_get_cr_bit(bb)));
1858       x86_set_reg(iop->ob_ptr,X86_CC_Z,hreg_t0,FALSE);
1859        
1860     /* result of AND between $ba and $bb */     /* result of AND between $ba and $bb */
1861     x86_alu_reg_reg(b->jit_ptr,X86_AND,X86_EBX,X86_EAX);     x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_t0,X86_EDX);
1862     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,0x01);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x01);
1863        
1864     /* set/clear $bd bit depending on the result */     /* set/clear $bd bit depending on the result */
1865     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,~(1 << (31 - bd)));     x86_alu_membase_imm(iop->ob_ptr,X86_AND,
1866     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,(31 - bd));                         X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
1867     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_ESI,X86_EBX);                         ~(1 << ppc32_get_cr_bit(bd)));
1868    
1869       x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_t0,ppc32_get_cr_bit(bd));
1870       x86_alu_membase_reg(iop->ob_ptr,X86_OR,
1871                           X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
1872                           hreg_t0);
1873    
1874     ppc32_store_cr(b,X86_ESI);     ppc32_jit_close_hreg_seq(cpu);
1875     return(0);     return(0);
1876  }  }
1877    
# Line 1105  DECLARE_INSN(CREQV) Line 1881  DECLARE_INSN(CREQV)
1881     int bd = bits(insn,21,25);     int bd = bits(insn,21,25);
1882     int bb = bits(insn,16,20);     int bb = bits(insn,16,20);
1883     int ba = bits(insn,11,15);     int ba = bits(insn,11,15);
1884       int hreg_t0;
1885       jit_op_t *iop;
1886    
1887       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
1888    
1889       ppc32_jit_start_hreg_seq(cpu,"creqv");
1890       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
1891       ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
1892    
1893       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(ba));
1894       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bb));
1895       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bd));
1896    
1897     ppc32_load_cr(b,X86_ESI);     iop = ppc32_op_emit_insn_output(cpu,3,"creqv");
1898    
1899     /* test $ba bit */     /* test $ba bit */
1900     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - ba)));     x86_test_membase_imm(iop->ob_ptr,
1901     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EAX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(ba)),
1902                            (1 << ppc32_get_cr_bit(ba)));
1903       x86_set_reg(iop->ob_ptr,X86_CC_NZ,X86_EDX,FALSE);
1904    
1905     /* test $bb bit */     /* test $bb bit */
1906     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - bb)));     x86_test_membase_imm(iop->ob_ptr,
1907     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EBX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bb)),
1908                            (1 << ppc32_get_cr_bit(bb)));
1909       x86_set_reg(iop->ob_ptr,X86_CC_NZ,hreg_t0,FALSE);
1910        
1911     /* result of XOR between $ba and $bb */     /* result of XOR between $ba and $bb */
1912     x86_alu_reg_reg(b->jit_ptr,X86_XOR,X86_EBX,X86_EAX);     x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_t0,X86_EDX);
1913     x86_not_reg(b->jit_ptr,X86_EBX);     x86_not_reg(iop->ob_ptr,hreg_t0);
1914     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,0x01);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x01);
1915        
1916     /* set/clear $bd bit depending on the result */     /* set/clear $bd bit depending on the result */
1917     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,~(1 << (31 - bd)));     x86_alu_membase_imm(iop->ob_ptr,X86_AND,
1918     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,(31 - bd));                         X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
1919     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_ESI,X86_EBX);                         ~(1 << ppc32_get_cr_bit(bd)));
1920    
1921       x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_t0,ppc32_get_cr_bit(bd));
1922       x86_alu_membase_reg(iop->ob_ptr,X86_OR,
1923                           X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
1924                           hreg_t0);
1925    
1926     ppc32_store_cr(b,X86_ESI);     ppc32_jit_close_hreg_seq(cpu);
1927     return(0);     return(0);
1928  }  }
1929    
# Line 1136  DECLARE_INSN(CRNAND) Line 1933  DECLARE_INSN(CRNAND)
1933     int bd = bits(insn,21,25);     int bd = bits(insn,21,25);
1934     int bb = bits(insn,16,20);     int bb = bits(insn,16,20);
1935     int ba = bits(insn,11,15);     int ba = bits(insn,11,15);
1936       int hreg_t0;
1937       jit_op_t *iop;
1938    
1939     ppc32_load_cr(b,X86_ESI);     ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
1940    
1941       ppc32_jit_start_hreg_seq(cpu,"crnand");
1942       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
1943       ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
1944    
1945       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(ba));
1946       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bb));
1947       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bd));
1948    
1949       iop = ppc32_op_emit_insn_output(cpu,3,"crnand");
1950    
1951     /* test $ba bit */     /* test $ba bit */
1952     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - ba)));     x86_test_membase_imm(iop->ob_ptr,
1953     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EAX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(ba)),
1954                            (1 << ppc32_get_cr_bit(ba)));
1955       x86_set_reg(iop->ob_ptr,X86_CC_NZ,X86_EDX,FALSE);
1956    
1957     /* test $bb bit */     /* test $bb bit */
1958     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - bb)));     x86_test_membase_imm(iop->ob_ptr,
1959     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EBX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bb)),
1960                            (1 << ppc32_get_cr_bit(bb)));
1961       x86_set_reg(iop->ob_ptr,X86_CC_NZ,hreg_t0,FALSE);
1962        
1963     /* result of NAND between $ba and $bb */     /* result of NAND between $ba and $bb */
1964     x86_alu_reg_reg(b->jit_ptr,X86_AND,X86_EBX,X86_EAX);     x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_t0,X86_EDX);
1965     x86_not_reg(b->jit_ptr,X86_EBX);     x86_not_reg(iop->ob_ptr,hreg_t0);
1966     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,0x01);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x01);
1967        
1968     /* set/clear $bd bit depending on the result */     /* set/clear $bd bit depending on the result */
1969     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,~(1 << (31 - bd)));     x86_alu_membase_imm(iop->ob_ptr,X86_AND,
1970     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,(31 - bd));                         X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
1971     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_ESI,X86_EBX);                         ~(1 << ppc32_get_cr_bit(bd)));
1972    
1973       x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_t0,ppc32_get_cr_bit(bd));
1974       x86_alu_membase_reg(iop->ob_ptr,X86_OR,
1975                           X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
1976                           hreg_t0);
1977    
1978     ppc32_store_cr(b,X86_ESI);     ppc32_jit_close_hreg_seq(cpu);
1979     return(0);     return(0);
1980  }  }
1981    
# Line 1167  DECLARE_INSN(CRNOR) Line 1985  DECLARE_INSN(CRNOR)
1985     int bd = bits(insn,21,25);     int bd = bits(insn,21,25);
1986     int bb = bits(insn,16,20);     int bb = bits(insn,16,20);
1987     int ba = bits(insn,11,15);     int ba = bits(insn,11,15);
1988       int hreg_t0;
1989       jit_op_t *iop;
1990    
1991       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
1992    
1993     ppc32_load_cr(b,X86_ESI);     ppc32_jit_start_hreg_seq(cpu,"crnor");
1994       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
1995       ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
1996    
1997       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(ba));
1998       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bb));
1999       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bd));
2000    
2001       iop = ppc32_op_emit_insn_output(cpu,3,"crnor");
2002    
2003     /* test $ba bit */     /* test $ba bit */
2004     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - ba)));     x86_test_membase_imm(iop->ob_ptr,
2005     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EAX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(ba)),
2006                            (1 << ppc32_get_cr_bit(ba)));
2007       x86_set_reg(iop->ob_ptr,X86_CC_NZ,X86_EDX,FALSE);
2008    
2009     /* test $bb bit */     /* test $bb bit */
2010     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - bb)));     x86_test_membase_imm(iop->ob_ptr,
2011     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EBX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bb)),
2012                            (1 << ppc32_get_cr_bit(bb)));
2013       x86_set_reg(iop->ob_ptr,X86_CC_NZ,hreg_t0,FALSE);
2014        
2015     /* result of NOR between $ba and $bb */     /* result of NOR between $ba and $bb */
2016     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EBX,X86_EAX);     x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_t0,X86_EDX);
2017     x86_not_reg(b->jit_ptr,X86_EBX);     x86_not_reg(iop->ob_ptr,hreg_t0);
2018     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,0x01);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x01);
2019        
2020     /* set/clear $bd bit depending on the result */     /* set/clear $bd bit depending on the result */
2021     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,~(1 << (31 - bd)));     x86_alu_membase_imm(iop->ob_ptr,X86_AND,
2022     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,(31 - bd));                         X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
2023     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_ESI,X86_EBX);                         ~(1 << ppc32_get_cr_bit(bd)));
2024    
2025       x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_t0,ppc32_get_cr_bit(bd));
2026       x86_alu_membase_reg(iop->ob_ptr,X86_OR,
2027                           X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
2028                           hreg_t0);
2029    
2030     ppc32_store_cr(b,X86_ESI);     ppc32_jit_close_hreg_seq(cpu);
2031     return(0);     return(0);
2032  }  }
2033    
# Line 1198  DECLARE_INSN(CROR) Line 2037  DECLARE_INSN(CROR)
2037     int bd = bits(insn,21,25);     int bd = bits(insn,21,25);
2038     int bb = bits(insn,16,20);     int bb = bits(insn,16,20);
2039     int ba = bits(insn,11,15);     int ba = bits(insn,11,15);
2040       int hreg_t0;
2041       jit_op_t *iop;
2042    
2043       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
2044    
2045       ppc32_jit_start_hreg_seq(cpu,"cror");
2046       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
2047       ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
2048    
2049     ppc32_load_cr(b,X86_ESI);     ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(ba));
2050       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bb));
2051       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bd));
2052    
2053       iop = ppc32_op_emit_insn_output(cpu,3,"cror");
2054    
2055     /* test $ba bit */     /* test $ba bit */
2056     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - ba)));     x86_test_membase_imm(iop->ob_ptr,
2057     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EAX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(ba)),
2058                            (1 << ppc32_get_cr_bit(ba)));
2059       x86_set_reg(iop->ob_ptr,X86_CC_NZ,X86_EDX,FALSE);
2060    
2061     /* test $bb bit */     /* test $bb bit */
2062     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - bb)));     x86_test_membase_imm(iop->ob_ptr,
2063     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EBX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bb)),
2064                            (1 << ppc32_get_cr_bit(bb)));
2065       x86_set_reg(iop->ob_ptr,X86_CC_NZ,hreg_t0,FALSE);
2066        
2067     /* result of OR between $ba and $bb */     /* result of OR between $ba and $bb */
2068     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EBX,X86_EAX);     x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_t0,X86_EDX);
2069     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,0x01);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x01);
2070        
2071     /* set/clear $bd bit depending on the result */     /* set/clear $bd bit depending on the result */
2072     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,~(1 << (31 - bd)));     x86_alu_membase_imm(iop->ob_ptr,X86_AND,
2073     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,(31 - bd));                         X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
2074     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_ESI,X86_EBX);                         ~(1 << ppc32_get_cr_bit(bd)));
2075    
2076       x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_t0,ppc32_get_cr_bit(bd));
2077       x86_alu_membase_reg(iop->ob_ptr,X86_OR,
2078                           X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
2079                           hreg_t0);
2080    
2081     ppc32_store_cr(b,X86_ESI);     ppc32_jit_close_hreg_seq(cpu);
2082     return(0);     return(0);
2083  }  }
2084    
# Line 1228  DECLARE_INSN(CRORC) Line 2088  DECLARE_INSN(CRORC)
2088     int bd = bits(insn,21,25);     int bd = bits(insn,21,25);
2089     int bb = bits(insn,16,20);     int bb = bits(insn,16,20);
2090     int ba = bits(insn,11,15);     int ba = bits(insn,11,15);
2091       int hreg_t0;
2092       jit_op_t *iop;
2093    
2094       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
2095    
2096       ppc32_jit_start_hreg_seq(cpu,"crorc");
2097       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
2098       ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
2099    
2100       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(ba));
2101       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bb));
2102       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bd));
2103    
2104     ppc32_load_cr(b,X86_ESI);     iop = ppc32_op_emit_insn_output(cpu,3,"crorc");
2105    
2106     /* test $ba bit */     /* test $ba bit */
2107     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - ba)));     x86_test_membase_imm(iop->ob_ptr,
2108     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EAX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(ba)),
2109                            (1 << ppc32_get_cr_bit(ba)));
2110       x86_set_reg(iop->ob_ptr,X86_CC_NZ,X86_EDX,FALSE);
2111    
2112     /* test $bb bit */     /* test $bb bit */
2113     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - bb)));     x86_test_membase_imm(iop->ob_ptr,
2114     x86_set_reg(b->jit_ptr,X86_CC_Z,X86_EBX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bb)),
2115                            (1 << ppc32_get_cr_bit(bb)));
2116       x86_set_reg(iop->ob_ptr,X86_CC_Z,hreg_t0,FALSE);
2117        
2118     /* result of ORC between $ba and $bb */     /* result of ORC between $ba and $bb */
2119     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EBX,X86_EAX);     x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_t0,X86_EDX);
2120     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,0x01);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x01);
2121        
2122     /* set/clear $bd bit depending on the result */     /* set/clear $bd bit depending on the result */
2123     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,~(1 << (31 - bd)));     x86_alu_membase_imm(iop->ob_ptr,X86_AND,
2124     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,(31 - bd));                         X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
2125     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_ESI,X86_EBX);                         ~(1 << ppc32_get_cr_bit(bd)));
2126    
2127       x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_t0,ppc32_get_cr_bit(bd));
2128       x86_alu_membase_reg(iop->ob_ptr,X86_OR,
2129                           X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
2130                           hreg_t0);
2131    
2132     ppc32_store_cr(b,X86_ESI);     ppc32_jit_close_hreg_seq(cpu);
2133     return(0);     return(0);
2134  }  }
2135    
# Line 1258  DECLARE_INSN(CRXOR) Line 2139  DECLARE_INSN(CRXOR)
2139     int bd = bits(insn,21,25);     int bd = bits(insn,21,25);
2140     int bb = bits(insn,16,20);     int bb = bits(insn,16,20);
2141     int ba = bits(insn,11,15);     int ba = bits(insn,11,15);
2142       int hreg_t0;
2143       jit_op_t *iop;
2144    
2145     ppc32_load_cr(b,X86_ESI);     ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
2146    
2147       ppc32_jit_start_hreg_seq(cpu,"crxor");
2148       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
2149       ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
2150    
2151       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(ba));
2152       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bb));
2153       ppc32_op_emit_require_flags(cpu,ppc32_get_cr_field(bd));
2154    
2155       iop = ppc32_op_emit_insn_output(cpu,3,"crxor");
2156    
2157     /* test $ba bit */     /* test $ba bit */
2158     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - ba)));     x86_test_membase_imm(iop->ob_ptr,
2159     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EAX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(ba)),
2160                            (1 << ppc32_get_cr_bit(ba)));
2161       x86_set_reg(iop->ob_ptr,X86_CC_NZ,X86_EDX,FALSE);
2162    
2163     /* test $bb bit */     /* test $bb bit */
2164     x86_test_reg_imm(b->jit_ptr,X86_ESI,(1 << (31 - bb)));     x86_test_membase_imm(iop->ob_ptr,
2165     x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_EBX,FALSE);                          X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bb)),
2166                            (1 << ppc32_get_cr_bit(bb)));
2167       x86_set_reg(iop->ob_ptr,X86_CC_NZ,hreg_t0,FALSE);
2168        
2169     /* result of XOR between $ba and $bb */     /* result of XOR between $ba and $bb */
2170     x86_alu_reg_reg(b->jit_ptr,X86_XOR,X86_EBX,X86_EAX);     x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_t0,X86_EDX);
2171     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,0x01);     x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x01);
2172        
2173     /* set/clear $bd bit depending on the result */     /* set/clear $bd bit depending on the result */
2174     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,~(1 << (31 - bd)));     x86_alu_membase_imm(iop->ob_ptr,X86_AND,
2175     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,(31 - bd));                         X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
2176     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_ESI,X86_EBX);                         ~(1 << ppc32_get_cr_bit(bd)));
2177    
2178       x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_t0,ppc32_get_cr_bit(bd));
2179       x86_alu_membase_reg(iop->ob_ptr,X86_OR,
2180                           X86_EDI,PPC32_CR_FIELD_OFFSET(ppc32_get_cr_field(bd)),
2181                           hreg_t0);
2182    
2183     ppc32_store_cr(b,X86_ESI);     ppc32_jit_close_hreg_seq(cpu);
2184     return(0);     return(0);
2185  }  }
2186    
# Line 1288  DECLARE_INSN(DIVWU) Line 2190  DECLARE_INSN(DIVWU)
2190     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
2191     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2192     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2193       int hreg_rb;
2194       jit_op_t *iop;
2195    
2196     ppc32_load_gpr(b,X86_EAX,ra);     ppc32_jit_start_hreg_seq(cpu,"divwu");
2197     ppc32_load_gpr(b,X86_EBX,rb);     ppc32_jit_alloc_hreg_forced(cpu,X86_EAX);
2198     ppc32_load_imm(b,X86_EDX,0);     ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
2199       hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
2200    
2201       /* $rd = $ra / $rb */
2202       ppc32_op_emit_load_gpr(cpu,X86_EAX,ra);
2203       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
2204    
2205     x86_div_reg(b->jit_ptr,X86_EBX,0);     iop = ppc32_op_emit_insn_output(cpu,2,"divwu");
2206     ppc32_store_gpr(b,rd,X86_EAX);     ppc32_load_imm(&iop->ob_ptr,X86_EDX,0);
2207    
2208     if (insn & 1) {     x86_div_reg(iop->ob_ptr,hreg_rb,0);
2209        x86_test_reg_reg(b->jit_ptr,X86_EAX,X86_EAX);  
2210        ppc32_update_cr0(b);     if (insn & 1)
2211     }        x86_test_reg_reg(iop->ob_ptr,X86_EAX,X86_EAX);
2212      
2213       ppc32_op_emit_store_gpr(cpu,rd,X86_EAX);
2214    
2215       if (insn & 1)
2216          ppc32_op_emit_update_flags(cpu,0,TRUE);
2217    
2218       /* edx:eax are directly modified: throw them */
2219       ppc32_op_emit_alter_host_reg(cpu,X86_EAX);
2220       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
2221    
2222       ppc32_jit_close_hreg_seq(cpu);
2223     return(0);     return(0);
2224  }  }
2225    
# Line 1310  DECLARE_INSN(EQV) Line 2229  DECLARE_INSN(EQV)
2229     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
2230     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2231     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2232       int hreg_rs,hreg_ra,hreg_rb;
2233       jit_op_t *iop;
2234    
2235     /* $ra = ~($rs ^ $rb) */     /* $ra = ~($rs ^ $rb) */
2236     ppc32_load_gpr(b,X86_EBX,rs);     ppc32_jit_start_hreg_seq(cpu,"eqv");
2237     ppc32_alu_gpr(b,X86_XOR,X86_EBX,rb);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
2238     x86_not_reg(b->jit_ptr,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
2239     ppc32_store_gpr(b,ra,X86_EBX);     hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
2240    
2241     if (insn & 1) {     ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
2242        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);     ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
2243        ppc32_update_cr0(b);  
2244       iop = ppc32_op_emit_insn_output(cpu,1,"eqv");
2245    
2246       if (ra == rs)
2247          x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_ra,hreg_rb);
2248       else if (ra == rb)
2249          x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_ra,hreg_rs);
2250       else {
2251          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
2252          x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_ra,hreg_rb);
2253     }     }
2254    
2255       x86_not_reg(iop->ob_ptr,hreg_ra);
2256    
2257       if (insn & 1)
2258          x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
2259    
2260       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
2261    
2262       if (insn & 1)
2263          ppc32_op_emit_update_flags(cpu,0,TRUE);
2264    
2265       ppc32_jit_close_hreg_seq(cpu);
2266     return(0);     return(0);
2267  }  }
2268    
# Line 1330  DECLARE_INSN(EXTSB) Line 2271  DECLARE_INSN(EXTSB)
2271  {    {  
2272     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
2273     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2274       int hreg_rs,hreg_ra;
2275       jit_op_t *iop;
2276    
2277     ppc32_load_gpr(b,X86_EBX,rs);     /* $ra = extsb($rs) */
2278     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,24);     ppc32_jit_start_hreg_seq(cpu,"extsb");
2279     x86_shift_reg_imm(b->jit_ptr,X86_SAR,X86_EBX,24);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
2280     ppc32_store_gpr(b,ra,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
2281    
2282     if (insn & 1) {     ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
2283        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);  
2284        ppc32_update_cr0(b);     iop = ppc32_op_emit_insn_output(cpu,2,"extsb");
    }  
2285    
2286       if (rs != ra)
2287          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
2288    
2289       x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_ra,24);
2290       x86_shift_reg_imm(iop->ob_ptr,X86_SAR,hreg_ra,24);
2291    
2292       if (insn & 1)
2293          x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
2294    
2295       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
2296    
2297       if (insn & 1)
2298          ppc32_op_emit_update_flags(cpu,0,TRUE);
2299    
2300       ppc32_jit_close_hreg_seq(cpu);
2301     return(0);     return(0);
2302  }  }
2303    
# Line 1349  DECLARE_INSN(EXTSH) Line 2306  DECLARE_INSN(EXTSH)
2306  {    {  
2307     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
2308     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2309       int hreg_rs,hreg_ra;
2310       jit_op_t *iop;
2311    
2312     ppc32_load_gpr(b,X86_EBX,rs);     /* $ra = extsh($rs) */
2313     x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,16);     ppc32_jit_start_hreg_seq(cpu,"extsh");
2314     x86_shift_reg_imm(b->jit_ptr,X86_SAR,X86_EBX,16);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
2315     ppc32_store_gpr(b,ra,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
2316    
2317     if (insn & 1) {     ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
2318        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);  
2319        ppc32_update_cr0(b);     iop = ppc32_op_emit_insn_output(cpu,2,"extsh");
2320     }  
2321       if (rs != ra)
2322          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
2323    
2324       x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_ra,16);
2325       x86_shift_reg_imm(iop->ob_ptr,X86_SAR,hreg_ra,16);
2326    
2327       if (insn & 1)
2328          x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
2329    
2330       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
2331    
2332       if (insn & 1)
2333          ppc32_op_emit_update_flags(cpu,0,TRUE);
2334    
2335       ppc32_jit_close_hreg_seq(cpu);
2336     return(0);     return(0);
2337  }  }
2338    
# Line 1370  DECLARE_INSN(LBZ) Line 2343  DECLARE_INSN(LBZ)
2343     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2344     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
2345    
2346     //ppc32_emit_memop(b,PPC_MEMOP_LBZ,ra,offset,rs,0);     //ppc32_emit_memop(cpu,b,PPC_MEMOP_LBZ,ra,offset,rs,0);
2347     ppc32_emit_memop_fast(b,0,PPC_MEMOP_LBZ,ra,offset,rs,ppc32_memop_fast_lbz);     ppc32_emit_memop_fast(cpu,b,0,PPC_MEMOP_LBZ,ra,offset,rs,
2348                             ppc32_memop_fast_lbz);
2349     return(0);     return(0);
2350  }  }
2351    
# Line 1382  DECLARE_INSN(LBZU) Line 2356  DECLARE_INSN(LBZU)
2356     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2357     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
2358    
2359     ppc32_emit_memop(b,PPC_MEMOP_LBZ,ra,offset,rs,1);     ppc32_emit_memop(cpu,b,PPC_MEMOP_LBZ,ra,offset,rs,1);
2360     return(0);     return(0);
2361  }  }
2362    
# Line 1393  DECLARE_INSN(LBZUX) Line 2367  DECLARE_INSN(LBZUX)
2367     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2368     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2369    
2370     ppc32_emit_memop_idx(b,PPC_MEMOP_LBZ,ra,rb,rs,1);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_LBZ,ra,rb,rs,1);
2371     return(0);     return(0);
2372  }  }
2373    
# Line 1404  DECLARE_INSN(LBZX) Line 2378  DECLARE_INSN(LBZX)
2378     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2379     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2380    
2381     ppc32_emit_memop_idx(b,PPC_MEMOP_LBZ,ra,rb,rs,0);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_LBZ,ra,rb,rs,0);
2382     return(0);     return(0);
2383  }  }
2384    
# Line 1415  DECLARE_INSN(LHA) Line 2389  DECLARE_INSN(LHA)
2389     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2390     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
2391    
2392     ppc32_emit_memop(b,PPC_MEMOP_LHA,ra,offset,rs,0);     ppc32_emit_memop(cpu,b,PPC_MEMOP_LHA,ra,offset,rs,0);
2393     return(0);     return(0);
2394  }  }
2395    
# Line 1426  DECLARE_INSN(LHAU) Line 2400  DECLARE_INSN(LHAU)
2400     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2401     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
2402    
2403     ppc32_emit_memop(b,PPC_MEMOP_LHA,ra,offset,rs,1);     ppc32_emit_memop(cpu,b,PPC_MEMOP_LHA,ra,offset,rs,1);
2404     return(0);     return(0);
2405  }  }
2406    
# Line 1437  DECLARE_INSN(LHAUX) Line 2411  DECLARE_INSN(LHAUX)
2411     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2412     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2413    
2414     ppc32_emit_memop_idx(b,PPC_MEMOP_LHA,ra,rb,rs,1);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_LHA,ra,rb,rs,1);
2415     return(0);     return(0);
2416  }  }
2417    
# Line 1448  DECLARE_INSN(LHAX) Line 2422  DECLARE_INSN(LHAX)
2422     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2423     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2424    
2425     ppc32_emit_memop_idx(b,PPC_MEMOP_LHA,ra,rb,rs,0);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_LHA,ra,rb,rs,0);
2426     return(0);     return(0);
2427  }  }
2428    
# Line 1459  DECLARE_INSN(LHZ) Line 2433  DECLARE_INSN(LHZ)
2433     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2434     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
2435    
2436     ppc32_emit_memop(b,PPC_MEMOP_LHZ,ra,offset,rs,0);     ppc32_emit_memop(cpu,b,PPC_MEMOP_LHZ,ra,offset,rs,0);
2437     return(0);     return(0);
2438  }  }
2439    
# Line 1470  DECLARE_INSN(LHZU) Line 2444  DECLARE_INSN(LHZU)
2444     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2445     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
2446    
2447     ppc32_emit_memop(b,PPC_MEMOP_LHZ,ra,offset,rs,1);     ppc32_emit_memop(cpu,b,PPC_MEMOP_LHZ,ra,offset,rs,1);
2448     return(0);     return(0);
2449  }  }
2450    
# Line 1481  DECLARE_INSN(LHZUX) Line 2455  DECLARE_INSN(LHZUX)
2455     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2456     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2457    
2458     ppc32_emit_memop_idx(b,PPC_MEMOP_LHZ,ra,rb,rs,1);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_LHZ,ra,rb,rs,1);
2459     return(0);     return(0);
2460  }  }
2461    
# Line 1492  DECLARE_INSN(LHZX) Line 2466  DECLARE_INSN(LHZX)
2466     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2467     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2468    
2469     ppc32_emit_memop_idx(b,PPC_MEMOP_LHZ,ra,rb,rs,0);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_LHZ,ra,rb,rs,0);
2470     return(0);     return(0);
2471  }  }
2472    
# Line 1504  DECLARE_INSN(LWZ) Line 2478  DECLARE_INSN(LWZ)
2478     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
2479    
2480     //ppc32_emit_memop(b,PPC_MEMOP_LWZ,ra,offset,rs,0);     //ppc32_emit_memop(b,PPC_MEMOP_LWZ,ra,offset,rs,0);
2481     ppc32_emit_memop_fast(b,0,PPC_MEMOP_LWZ,ra,offset,rs,ppc32_memop_fast_lwz);     ppc32_emit_memop_fast(cpu,b,0,PPC_MEMOP_LWZ,ra,offset,rs,
2482                             ppc32_memop_fast_lwz);
2483     return(0);     return(0);
2484  }  }
2485    
# Line 1515  DECLARE_INSN(LWZU) Line 2490  DECLARE_INSN(LWZU)
2490     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2491     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
2492    
2493     ppc32_emit_memop(b,PPC_MEMOP_LWZ,ra,offset,rs,1);     ppc32_emit_memop(cpu,b,PPC_MEMOP_LWZ,ra,offset,rs,1);
2494     return(0);     return(0);
2495  }  }
2496    
# Line 1526  DECLARE_INSN(LWZUX) Line 2501  DECLARE_INSN(LWZUX)
2501     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2502     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2503    
2504     ppc32_emit_memop_idx(b,PPC_MEMOP_LWZ,ra,rb,rs,1);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_LWZ,ra,rb,rs,1);
2505     return(0);     return(0);
2506  }  }
2507    
# Line 1537  DECLARE_INSN(LWZX) Line 2512  DECLARE_INSN(LWZX)
2512     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2513     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2514    
2515     ppc32_emit_memop_idx(b,PPC_MEMOP_LWZ,ra,rb,rs,0);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_LWZ,ra,rb,rs,0);
2516     return(0);     return(0);
2517  }  }
2518    
# Line 1546  DECLARE_INSN(MCRF) Line 2521  DECLARE_INSN(MCRF)
2521  {  {
2522     int rd = bits(insn,23,25);     int rd = bits(insn,23,25);
2523     int rs = bits(insn,18,20);     int rs = bits(insn,18,20);
2524     m_uint32_t dmask;     int hreg_t0;
2525       jit_op_t *iop;
2526    
2527       ppc32_jit_start_hreg_seq(cpu,"mcrf");
2528       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);  
2529       ppc32_op_emit_require_flags(cpu,rs);
2530    
2531       iop = ppc32_op_emit_insn_output(cpu,1,"mcrf");
2532    
2533       /* Load "rs" field in %edx */
2534       x86_mov_reg_membase(iop->ob_ptr,hreg_t0,
2535                           X86_EDI,PPC32_CR_FIELD_OFFSET(rs),4);
2536    
2537       /* Store it in "rd" field */
2538       x86_mov_membase_reg(iop->ob_ptr,X86_EDI,PPC32_CR_FIELD_OFFSET(rd),
2539                           hreg_t0,4);
2540    
2541     /* %eax = %ebx = CR */     ppc32_jit_close_hreg_seq(cpu);
    ppc32_load_cr(b,X86_EAX);  
    x86_mov_reg_reg(b->jit_ptr,X86_EBX,X86_EAX,4);  
   
    x86_shift_reg_imm(b->jit_ptr,X86_SHR,X86_EBX,(28 - (rs << 2)));  
    x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,0x0F);  
    x86_shift_reg_imm(b->jit_ptr,X86_SHL,X86_EBX,(28 - (rd << 2)));  
   
    /* clear the destination bits */  
    dmask = (0xF0000000 >> (rd << 2));  
    x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,~dmask);  
   
    /* set the new field value */  
    x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EAX,X86_EBX);  
    ppc32_store_cr(b,X86_EAX);  
2542     return(0);     return(0);
2543  }  }
2544    
# Line 1570  DECLARE_INSN(MCRF) Line 2546  DECLARE_INSN(MCRF)
2546  DECLARE_INSN(MFCR)  DECLARE_INSN(MFCR)
2547  {  {
2548     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
2549       int hreg_rd,hreg_t0;
2550       jit_op_t *iop;
2551       int i;
2552    
2553       ppc32_jit_start_hreg_seq(cpu,"mfcr");
2554       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
2555       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
2556       ppc32_op_emit_require_flags(cpu,JIT_OP_PPC_ALL_FLAGS);
2557    
2558       iop = ppc32_op_emit_insn_output(cpu,3,"mfcr");
2559    
2560       x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_rd,hreg_rd);
2561    
2562     ppc32_load_cr(b,X86_EAX);     for(i=0;i<8;i++) {
2563     ppc32_store_gpr(b,rd,X86_EAX);        /* load field in %edx */
2564          x86_mov_reg_membase(iop->ob_ptr,hreg_t0,
2565                              X86_EDI,PPC32_CR_FIELD_OFFSET(i),4);
2566          x86_shift_reg_imm(iop->ob_ptr,X86_SHL,hreg_rd,4);
2567          x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_rd,hreg_t0);
2568       }
2569    
2570       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
2571    
2572       ppc32_jit_close_hreg_seq(cpu);
2573     return(0);     return(0);
2574  }  }
2575    
# Line 1580  DECLARE_INSN(MFCR) Line 2577  DECLARE_INSN(MFCR)
2577  DECLARE_INSN(MFMSR)  DECLARE_INSN(MFMSR)
2578  {  {
2579     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
2580       int hreg_rd;
2581       jit_op_t *iop;
2582    
2583       ppc32_jit_start_hreg_seq(cpu,"mfmsr");
2584       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
2585    
2586       iop = ppc32_op_emit_insn_output(cpu,1,"mfmsr");
2587       x86_mov_reg_membase(iop->ob_ptr,hreg_rd,X86_EDI,OFFSET(cpu_ppc_t,msr),4);
2588       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
2589    
2590     x86_mov_reg_membase(b->jit_ptr,X86_EAX,X86_EDI,OFFSET(cpu_ppc_t,msr),4);     ppc32_jit_close_hreg_seq(cpu);
    ppc32_store_gpr(b,rd,X86_EAX);  
2591     return(0);     return(0);
2592  }  }
2593    
# Line 1591  DECLARE_INSN(MFSR) Line 2596  DECLARE_INSN(MFSR)
2596  {  {
2597     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
2598     int sr = bits(insn,16,19);     int sr = bits(insn,16,19);
2599       int hreg_rd;
2600       jit_op_t *iop;
2601    
2602     x86_mov_reg_membase(b->jit_ptr,X86_EAX,     ppc32_jit_start_hreg_seq(cpu,"mfsr");
2603       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
2604    
2605       iop = ppc32_op_emit_insn_output(cpu,1,"mfsr");
2606    
2607       x86_mov_reg_membase(iop->ob_ptr,hreg_rd,
2608                         X86_EDI,(OFFSET(cpu_ppc_t,sr) + (sr << 2)),4);                         X86_EDI,(OFFSET(cpu_ppc_t,sr) + (sr << 2)),4);
2609     ppc32_store_gpr(b,rd,X86_EAX);     ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
2610    
2611       ppc32_jit_close_hreg_seq(cpu);
2612     return(0);     return(0);
2613  }  }
2614    
# Line 1603  DECLARE_INSN(MTCRF) Line 2617  DECLARE_INSN(MTCRF)
2617  {  {
2618     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
2619     int crm = bits(insn,12,19);     int crm = bits(insn,12,19);
2620     m_uint32_t mask = 0;     int hreg_rs,hreg_t0;
2621       jit_op_t *iop;
2622     int i;     int i;
2623    
2624       ppc32_jit_start_hreg_seq(cpu,"mtcrf");
2625       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
2626       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
2627    
2628       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
2629    
2630       iop = ppc32_op_emit_insn_output(cpu,3,"mtcrf");
2631    
2632     for(i=0;i<8;i++)     for(i=0;i<8;i++)
2633        if (crm & (1 << i))        if (crm & (1 << (7 - i))) {
2634           mask |= 0xF << (i << 2);           x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_rs,4);
2635    
2636     ppc32_load_cr(b,X86_EAX);           if (i != 7)
2637     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,~mask);              x86_shift_reg_imm(iop->ob_ptr,X86_SHR,hreg_t0,28 - (i << 2));
2638    
2639             x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x0F);
2640             x86_mov_membase_reg(iop->ob_ptr,X86_EDI,PPC32_CR_FIELD_OFFSET(i),
2641                                 hreg_t0,4);
2642          }
2643    
2644     ppc32_load_gpr(b,X86_EDX,rs);     ppc32_op_emit_basic_opcode(cpu,JIT_OP_TRASH_FLAGS);
    x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EDX,mask);  
2645    
2646     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EDX,X86_EAX);     ppc32_jit_close_hreg_seq(cpu);
    ppc32_store_cr(b,X86_EDX);  
2647     return(0);     return(0);
2648  }  }
2649    
# Line 1627  DECLARE_INSN(MULHW) Line 2653  DECLARE_INSN(MULHW)
2653     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
2654     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2655     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2656       int hreg_rb;
2657       jit_op_t *iop;
2658    
2659     ppc32_load_gpr(b,X86_EAX,ra);     ppc32_jit_start_hreg_seq(cpu,"mulhw");
2660     ppc32_load_gpr(b,X86_EBX,rb);     ppc32_jit_alloc_hreg_forced(cpu,X86_EAX);
2661     x86_mul_reg(b->jit_ptr,X86_EBX,1);     ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
2662     ppc32_store_gpr(b,rd,X86_EDX);     hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
2663    
2664       ppc32_op_emit_load_gpr(cpu,X86_EAX,ra);
2665       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
2666    
2667       /* rd = hi(ra * rb) */
2668       iop = ppc32_op_emit_insn_output(cpu,2,"mulhw");
2669       x86_mul_reg(iop->ob_ptr,hreg_rb,1);
2670    
2671     if (insn & 1) {     if (insn & 1)
2672        x86_test_reg_reg(b->jit_ptr,X86_EDX,X86_EDX);        x86_test_reg_reg(iop->ob_ptr,X86_EDX,X86_EDX);
       ppc32_update_cr0(b);  
    }  
2673    
2674       ppc32_op_emit_store_gpr(cpu,rd,X86_EDX);
2675    
2676       if (insn & 1)
2677          ppc32_op_emit_update_flags(cpu,0,TRUE);
2678    
2679       /* edx:eax are directly modified: throw them */
2680       ppc32_op_emit_alter_host_reg(cpu,X86_EAX);
2681       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
2682    
2683       ppc32_jit_close_hreg_seq(cpu);
2684     return(0);     return(0);
2685  }  }
2686    
# Line 1647  DECLARE_INSN(MULHWU) Line 2690  DECLARE_INSN(MULHWU)
2690     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
2691     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2692     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2693       int hreg_rb;
2694       jit_op_t *iop;
2695    
2696     ppc32_load_gpr(b,X86_EAX,ra);     ppc32_jit_start_hreg_seq(cpu,"mulhwu");
2697     ppc32_load_gpr(b,X86_EBX,rb);     ppc32_jit_alloc_hreg_forced(cpu,X86_EAX);
2698     x86_mul_reg(b->jit_ptr,X86_EBX,0);     ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
2699     ppc32_store_gpr(b,rd,X86_EDX);     hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
2700    
2701       ppc32_op_emit_load_gpr(cpu,X86_EAX,ra);
2702       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
2703    
2704       /* rd = hi(ra * rb) */
2705       iop = ppc32_op_emit_insn_output(cpu,2,"mulhwu");
2706       x86_mul_reg(iop->ob_ptr,hreg_rb,0);
2707    
2708     if (insn & 1) {     if (insn & 1)
2709        x86_test_reg_reg(b->jit_ptr,X86_EDX,X86_EDX);        x86_test_reg_reg(iop->ob_ptr,X86_EDX,X86_EDX);
2710        ppc32_update_cr0(b);  
2711     }     ppc32_op_emit_store_gpr(cpu,rd,X86_EDX);
2712    
2713       if (insn & 1)
2714          ppc32_op_emit_update_flags(cpu,0,TRUE);
2715    
2716       /* edx:eax are directly modified: throw them */
2717       ppc32_op_emit_alter_host_reg(cpu,X86_EAX);
2718       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
2719    
2720       ppc32_jit_close_hreg_seq(cpu);
2721     return(0);     return(0);
2722  }  }
2723    
# Line 1667  DECLARE_INSN(MULLI) Line 2727  DECLARE_INSN(MULLI)
2727     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
2728     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2729     m_uint32_t imm = bits(insn,0,15);     m_uint32_t imm = bits(insn,0,15);
2730       int hreg_t0;
2731       jit_op_t *iop;
2732    
2733       ppc32_jit_start_hreg_seq(cpu,"mulli");
2734       ppc32_jit_alloc_hreg_forced(cpu,X86_EAX);
2735       ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
2736       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
2737    
2738       ppc32_op_emit_load_gpr(cpu,X86_EAX,ra);
2739    
2740     ppc32_load_gpr(b,X86_EAX,ra);     /* rd = lo(ra * imm) */
2741     ppc32_load_imm(b,X86_EBX,sign_extend_32(imm,16));     iop = ppc32_op_emit_insn_output(cpu,2,"mulli");
2742    
2743     x86_mul_reg(b->jit_ptr,X86_EBX,1);     ppc32_load_imm(&iop->ob_ptr,hreg_t0,sign_extend_32(imm,16));
2744     ppc32_store_gpr(b,rd,X86_EAX);     x86_mul_reg(iop->ob_ptr,hreg_t0,1);
2745       ppc32_op_emit_store_gpr(cpu,rd,X86_EAX);
2746    
2747       /* edx:eax are directly modified: throw them */
2748       ppc32_op_emit_alter_host_reg(cpu,X86_EAX);
2749       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
2750    
2751       ppc32_jit_close_hreg_seq(cpu);
2752     return(0);     return(0);
2753  }  }
2754    
# Line 1682  DECLARE_INSN(MULLW) Line 2758  DECLARE_INSN(MULLW)
2758     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
2759     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2760     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2761       int hreg_rb;
2762       jit_op_t *iop;
2763    
2764     ppc32_load_gpr(b,X86_EAX,ra);     ppc32_jit_start_hreg_seq(cpu,"mullw");
2765     ppc32_load_gpr(b,X86_EBX,rb);     ppc32_jit_alloc_hreg_forced(cpu,X86_EAX);
2766     x86_mul_reg(b->jit_ptr,X86_EBX,1);     ppc32_jit_alloc_hreg_forced(cpu,X86_EDX);
2767     ppc32_store_gpr(b,rd,X86_EAX);     hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
2768    
2769       ppc32_op_emit_load_gpr(cpu,X86_EAX,ra);
2770       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
2771    
2772       /* rd = lo(ra * rb) */
2773       iop = ppc32_op_emit_insn_output(cpu,2,"mullw");
2774       x86_mul_reg(iop->ob_ptr,hreg_rb,1);
2775    
2776     if (insn & 1) {     if (insn & 1)
2777        x86_test_reg_reg(b->jit_ptr,X86_EAX,X86_EAX);        x86_test_reg_reg(iop->ob_ptr,X86_EAX,X86_EAX);
2778        ppc32_update_cr0(b);  
2779     }     ppc32_op_emit_store_gpr(cpu,rd,X86_EAX);
2780    
2781       if (insn & 1)
2782          ppc32_op_emit_update_flags(cpu,0,TRUE);
2783    
2784       /* edx:eax are directly modified: throw them */
2785       ppc32_op_emit_alter_host_reg(cpu,X86_EAX);
2786       ppc32_op_emit_alter_host_reg(cpu,X86_EDX);
2787    
2788       ppc32_jit_close_hreg_seq(cpu);
2789     return(0);     return(0);
2790  }  }
2791    
# Line 1702  DECLARE_INSN(NAND) Line 2795  DECLARE_INSN(NAND)
2795     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
2796     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2797     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2798       int hreg_rs,hreg_ra,hreg_rb;
2799       jit_op_t *iop;
2800    
2801     /* $ra = ~($rs & $rb) */     /* $ra = ~($rs & $rb) */
2802     ppc32_load_gpr(b,X86_EBX,rs);     ppc32_jit_start_hreg_seq(cpu,"nand");
2803     ppc32_alu_gpr(b,X86_AND,X86_EBX,rb);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
2804     x86_not_reg(b->jit_ptr,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
2805     ppc32_store_gpr(b,ra,X86_EBX);     hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
2806    
2807     if (insn & 1) {     ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
2808        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);     ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
2809        ppc32_update_cr0(b);  
2810       iop = ppc32_op_emit_insn_output(cpu,2,"nand");
2811    
2812       if (ra == rs)
2813          x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_ra,hreg_rb);
2814       else if (ra == rb)
2815          x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_ra,hreg_rs);
2816       else {
2817          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
2818          x86_alu_reg_reg(iop->ob_ptr,X86_AND,hreg_ra,hreg_rb);
2819     }     }
2820    
2821       x86_not_reg(iop->ob_ptr,hreg_ra);
2822    
2823       if (insn & 1)
2824          x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
2825    
2826       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
2827    
2828       if (insn & 1)
2829          ppc32_op_emit_update_flags(cpu,0,TRUE);
2830    
2831       ppc32_jit_close_hreg_seq(cpu);
2832     return(0);     return(0);
2833  }  }
2834    
# Line 1722  DECLARE_INSN(NEG) Line 2837  DECLARE_INSN(NEG)
2837  {  {
2838     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
2839     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2840       int hreg_rd,hreg_ra;
2841       jit_op_t *iop;
2842    
2843     ppc32_load_gpr(b,X86_EBX,ra);     /* $rd = neg($ra) */
2844     x86_neg_reg(b->jit_ptr,X86_EBX);     ppc32_jit_start_hreg_seq(cpu,"neg");
2845     ppc32_store_gpr(b,rd,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
2846       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
2847    
2848     if (insn & 1) {     ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
2849        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);  
2850        ppc32_update_cr0(b);     iop = ppc32_op_emit_insn_output(cpu,1,"neg");
2851     }  
2852       if (rd != ra)
2853          x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_ra,4);
2854    
2855       x86_neg_reg(iop->ob_ptr,hreg_rd);
2856    
2857       if (insn & 1)
2858          x86_test_reg_reg(iop->ob_ptr,hreg_rd,hreg_rd);
2859    
2860       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
2861    
2862       if (insn & 1)
2863          ppc32_op_emit_update_flags(cpu,0,TRUE);
2864    
2865       ppc32_jit_close_hreg_seq(cpu);
2866     return(0);     return(0);
2867  }  }
2868    
# Line 1741  DECLARE_INSN(NOR) Line 2872  DECLARE_INSN(NOR)
2872     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
2873     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2874     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2875       int hreg_rs,hreg_ra,hreg_rb;
2876       jit_op_t *iop;
2877    
2878     /* $ra = ~($rs | $rb) */     /* $ra = ~($rs | $rb) */
2879     ppc32_load_gpr(b,X86_EBX,rs);     ppc32_jit_start_hreg_seq(cpu,"nor");
2880     ppc32_alu_gpr(b,X86_OR,X86_EBX,rb);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
2881     x86_not_reg(b->jit_ptr,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
2882     ppc32_store_gpr(b,ra,X86_EBX);     hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
2883    
2884     if (insn & 1) {     ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
2885        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);     ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
2886        ppc32_update_cr0(b);  
2887       iop = ppc32_op_emit_insn_output(cpu,2,"nor");
2888    
2889       if (ra == rs)
2890          x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_ra,hreg_rb);
2891       else if (ra == rb)
2892          x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_ra,hreg_rs);
2893       else {
2894          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
2895          x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_ra,hreg_rb);
2896     }     }
2897    
2898       x86_not_reg(iop->ob_ptr,hreg_ra);
2899    
2900       if (insn & 1)
2901          x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
2902    
2903       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
2904    
2905       if (insn & 1)
2906          ppc32_op_emit_update_flags(cpu,0,TRUE);
2907    
2908       ppc32_jit_close_hreg_seq(cpu);
2909     return(0);     return(0);
2910  }  }
2911    
# Line 1762  DECLARE_INSN(OR) Line 2915  DECLARE_INSN(OR)
2915     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
2916     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2917     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2918       int hreg_rs,hreg_ra,hreg_rb;
2919       jit_op_t *iop;
2920    
2921     ppc32_load_gpr(b,X86_ECX,rs);     /* $ra = $rs | $rb */
2922       ppc32_jit_start_hreg_seq(cpu,"or");
2923       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
2924       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
2925       hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
2926    
2927     if (rs != rb)     /* special optimization for move/nop operation */
2928        ppc32_alu_gpr(b,X86_OR,X86_ECX,rb);     if (rs == rb) {
2929          ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
2930          iop = ppc32_op_emit_insn_output(cpu,2,"or");
2931    
2932     ppc32_store_gpr(b,ra,X86_ECX);        if (ra != rs)
2933             x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
2934    
2935     if (insn & 1) {        if (insn & 1)
2936        if (rs == rb)           x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
2937           x86_test_reg_reg(b->jit_ptr,X86_ECX,X86_ECX);  
2938        ppc32_update_cr0(b);        ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
2939    
2940          if (insn & 1)
2941             ppc32_op_emit_update_flags(cpu,0,TRUE);
2942    
2943          ppc32_jit_close_hreg_seq(cpu);
2944          return(0);
2945       }
2946    
2947       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
2948       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
2949    
2950       iop = ppc32_op_emit_insn_output(cpu,2,"or");
2951    
2952       if (ra == rs) {
2953          x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_ra,hreg_rb);
2954       } else if (ra == rb)
2955          x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_ra,hreg_rs);
2956       else {
2957          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
2958          x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_ra,hreg_rb);
2959     }     }
2960    
2961       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
2962    
2963       if (insn & 1)
2964          ppc32_op_emit_update_flags(cpu,0,TRUE);
2965    
2966       ppc32_jit_close_hreg_seq(cpu);
2967     return(0);     return(0);
2968  }  }
2969    
# Line 1785  DECLARE_INSN(ORC) Line 2973  DECLARE_INSN(ORC)
2973     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
2974     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
2975     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
2976       int hreg_rs,hreg_ra,hreg_rb,hreg_t0;
2977       jit_op_t *iop;
2978    
2979       /* $ra = $rs & ~$rb */
2980       ppc32_jit_start_hreg_seq(cpu,"orc");
2981       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
2982       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
2983       hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
2984    
2985       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
2986       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
2987    
2988       iop = ppc32_op_emit_insn_output(cpu,1,"orc");
2989    
2990       /* $t0 = ~$rb */
2991       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
2992       x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_rb,4);
2993       x86_not_reg(iop->ob_ptr,hreg_t0);
2994    
2995       /* $ra = $rs | $t0 */
2996       if (ra == rs)
2997          x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_ra,hreg_t0);
2998       else {
2999          x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_t0,hreg_rs);
3000          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_t0,4);
3001       }
3002    
3003     /* $ra = $rs | ~$rb */     ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
    ppc32_load_gpr(b,X86_EBX,rb);  
    x86_not_reg(b->jit_ptr,X86_EBX);  
    ppc32_alu_gpr(b,X86_OR,X86_EBX,rs);  
    ppc32_store_gpr(b,ra,X86_EBX);  
3004    
3005     if (insn & 1)     if (insn & 1)
3006        ppc32_update_cr0(b);        ppc32_op_emit_update_flags(cpu,0,TRUE);
3007    
3008       ppc32_jit_close_hreg_seq(cpu);
3009     return(0);     return(0);
3010  }  }
3011    
# Line 1804  DECLARE_INSN(ORI) Line 3015  DECLARE_INSN(ORI)
3015     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
3016     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3017     m_uint16_t imm = bits(insn,0,15);     m_uint16_t imm = bits(insn,0,15);
3018       m_uint32_t tmp = imm;
3019       int hreg_rs,hreg_ra;
3020       jit_op_t *iop;
3021    
3022     /* $ra = $rs | imm */     /* $ra = $rs | imm */
3023     ppc32_load_imm(b,X86_EBX,imm);     ppc32_jit_start_hreg_seq(cpu,"ori");
3024     ppc32_alu_gpr(b,X86_OR,X86_EBX,rs);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3025     ppc32_store_gpr(b,ra,X86_EBX);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3026    
3027       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
3028    
3029       iop = ppc32_op_emit_insn_output(cpu,1,"ori");
3030    
3031       if (ra != rs)
3032          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
3033    
3034       x86_alu_reg_imm(iop->ob_ptr,X86_OR,hreg_ra,tmp);
3035       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3036    
3037       ppc32_jit_close_hreg_seq(cpu);
3038     return(0);     return(0);
3039  }  }
3040    
# Line 1817  DECLARE_INSN(ORIS) Line 3043  DECLARE_INSN(ORIS)
3043  {  {
3044     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
3045     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3046     m_uint32_t imm = bits(insn,0,15);     m_uint16_t imm = bits(insn,0,15);
3047       m_uint32_t tmp = imm << 16;
3048       int hreg_rs,hreg_ra;
3049       jit_op_t *iop;
3050    
3051       /* $ra = $rs | imm */
3052       ppc32_jit_start_hreg_seq(cpu,"oris");
3053       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3054       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3055    
3056       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
3057    
3058     /* $ra = $rs | (imm << 16) */     iop = ppc32_op_emit_insn_output(cpu,1,"oris");
3059     ppc32_load_imm(b,X86_EBX,imm << 16);  
3060     ppc32_alu_gpr(b,X86_OR,X86_EBX,rs);     if (ra != rs)
3061     ppc32_store_gpr(b,ra,X86_EBX);        x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
3062    
3063       x86_alu_reg_imm(iop->ob_ptr,X86_OR,hreg_ra,tmp);
3064       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3065    
3066       ppc32_jit_close_hreg_seq(cpu);
3067     return(0);     return(0);
3068  }  }
3069    
# Line 1835  DECLARE_INSN(RLWIMI) Line 3076  DECLARE_INSN(RLWIMI)
3076     int mb = bits(insn,6,10);     int mb = bits(insn,6,10);
3077     int me = bits(insn,1,5);     int me = bits(insn,1,5);
3078     register m_uint32_t mask;     register m_uint32_t mask;
3079       int hreg_rs,hreg_ra,hreg_t0;
3080       jit_op_t *iop;
3081    
3082       ppc32_jit_start_hreg_seq(cpu,"rlwimi");
3083       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
3084       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3085       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3086    
3087       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
3088       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
3089    
3090     mask = ppc32_rotate_mask(mb,me);     mask = ppc32_rotate_mask(mb,me);
3091    
3092     /* Apply inverse mask to %eax "ra" */     iop = ppc32_op_emit_insn_output(cpu,2,"rlwimi");
3093     ppc32_load_gpr(b,X86_EAX,ra);  
3094       /* Apply inverse mask to $ra */
3095     if (mask != 0)     if (mask != 0)
3096        x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,~mask);        x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_ra,~mask);
3097    
3098     /* Rotate %ebx ("rs") of "sh" bits and apply the mask */     /* Rotate $rs of "sh" bits and apply the mask */
3099     ppc32_load_gpr(b,X86_EBX,rs);     x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_rs,4);
3100    
3101     if (sh != 0)     if (sh != 0)
3102     x86_shift_reg_imm(b->jit_ptr,X86_ROL,X86_EBX,sh);        x86_shift_reg_imm(iop->ob_ptr,X86_ROL,hreg_t0,sh);
3103    
3104     if (mask != 0xFFFFFFFF)     if (mask != 0xFFFFFFFF)
3105        x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,mask);        x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,mask);
3106    
3107     /* Store the result */     /* Store the result */
3108     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EBX,X86_EAX);     x86_alu_reg_reg(iop->ob_ptr,X86_OR,hreg_ra,hreg_t0);
3109     ppc32_store_gpr(b,ra,X86_EBX);     ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3110    
3111     if (insn & 1)     if (insn & 1)
3112        ppc32_update_cr0(b);        ppc32_op_emit_update_flags(cpu,0,TRUE);
3113    
3114       ppc32_jit_close_hreg_seq(cpu);
3115     return(0);     return(0);
3116  }  }
3117    
# Line 1871  DECLARE_INSN(RLWINM) Line 3124  DECLARE_INSN(RLWINM)
3124     int mb = bits(insn,6,10);     int mb = bits(insn,6,10);
3125     int me = bits(insn,1,5);     int me = bits(insn,1,5);
3126     register m_uint32_t mask;     register m_uint32_t mask;
3127       int hreg_rs,hreg_ra;
3128       jit_op_t *iop;
3129    
3130       ppc32_jit_start_hreg_seq(cpu,"rlwinm");
3131       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3132       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3133    
3134       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
3135    
3136       iop = ppc32_op_emit_insn_output(cpu,2,"rlwinm");
3137    
3138       /* Rotate $rs of "sh" bits and apply the mask */
3139     mask = ppc32_rotate_mask(mb,me);     mask = ppc32_rotate_mask(mb,me);
3140    
3141     /* Rotate %ebx ("rs") of "sh" bits and apply the mask */     if (rs != ra)
3142     ppc32_load_gpr(b,X86_EBX,rs);        x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
3143    
3144     if (sh != 0)     if (sh != 0)
3145        x86_shift_reg_imm(b->jit_ptr,X86_ROL,X86_EBX,sh);        x86_shift_reg_imm(iop->ob_ptr,X86_ROL,hreg_ra,sh);
3146    
3147     if (mask != 0xFFFFFFFF)     if (mask != 0xFFFFFFFF)
3148        x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,mask);        x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_ra,mask);
3149    
3150     ppc32_store_gpr(b,ra,X86_EBX);     if (insn & 1)
3151          x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
3152    
3153     if (insn & 1) {     ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3154        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);  
3155        ppc32_update_cr0(b);     if (insn & 1)
3156     }        ppc32_op_emit_update_flags(cpu,0,TRUE);
3157    
3158       ppc32_jit_close_hreg_seq(cpu);
3159     return(0);     return(0);
3160  }  }
3161    
# Line 1902  DECLARE_INSN(RLWNM) Line 3168  DECLARE_INSN(RLWNM)
3168     int mb = bits(insn,6,10);     int mb = bits(insn,6,10);
3169     int me = bits(insn,1,5);     int me = bits(insn,1,5);
3170     register m_uint32_t mask;     register m_uint32_t mask;
3171       int hreg_rs,hreg_ra,hreg_t0;
3172       jit_op_t *iop;
3173    
3174     mask = ppc32_rotate_mask(mb,me);     /* ecx is directly modified: throw it */
3175       ppc32_op_emit_alter_host_reg(cpu,X86_ECX);
3176    
3177       ppc32_jit_start_hreg_seq(cpu,"rlwnm");
3178       ppc32_jit_alloc_hreg_forced(cpu,X86_ECX);
3179    
3180       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
3181       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3182       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3183    
3184       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
3185       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
3186       ppc32_op_emit_load_gpr(cpu,X86_ECX,rb);
3187    
3188       iop = ppc32_op_emit_insn_output(cpu,2,"rlwnm");
3189    
3190     /* Load the shift register ("sh") */     /* Load the shift register ("sh") */
3191     ppc32_load_gpr(b,X86_ECX,rb);     mask = ppc32_rotate_mask(mb,me);
3192    
3193     /* Rotate %ebx ("rs") and apply the mask */     /* Rotate $rs and apply the mask */
3194     ppc32_load_gpr(b,X86_EBX,rs);     x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_rs,4);
3195     x86_shift_reg(b->jit_ptr,X86_ROL,X86_EBX);  
3196       x86_shift_reg(iop->ob_ptr,X86_ROL,hreg_t0);
3197    
3198     if (mask != 0xFFFFFFFF)     if (mask != 0xFFFFFFFF)
3199        x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EBX,mask);        x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,mask);
3200    
3201     ppc32_store_gpr(b,ra,X86_EBX);     x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_t0,4);
3202    
3203     if (insn & 1) {     if (insn & 1)
3204        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);        x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
       ppc32_update_cr0(b);  
    }  
3205    
3206       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3207    
3208       if (insn & 1)
3209          ppc32_op_emit_update_flags(cpu,0,TRUE);
3210    
3211       ppc32_jit_close_hreg_seq(cpu);
3212     return(0);     return(0);
3213  }  }
3214    
# Line 1932  DECLARE_INSN(SLW) Line 3219  DECLARE_INSN(SLW)
3219     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3220     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3221     u_char *test1;     u_char *test1;
3222       int hreg_rs,hreg_ra,hreg_t0;
3223       jit_op_t *iop;
3224    
3225     /* If count >= 32, then null result */     /* ecx is directly modified: throw it */
3226     ppc32_load_gpr(b,X86_ECX,rb);     ppc32_op_emit_alter_host_reg(cpu,X86_ECX);
    x86_alu_reg_reg(b->jit_ptr,X86_XOR,X86_EBX,X86_EBX);  
   
    x86_test_reg_imm(b->jit_ptr,X86_ECX,0x20);  
    test1 = b->jit_ptr;  
    x86_branch8(b->jit_ptr, X86_CC_NZ, 0, 1);  
3227    
3228     ppc32_load_gpr(b,X86_EBX,rs);     ppc32_jit_start_hreg_seq(cpu,"slw");
3229     x86_shift_reg(b->jit_ptr,X86_SHL,X86_EBX);     ppc32_jit_alloc_hreg_forced(cpu,X86_ECX);
3230       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
3231       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3232       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3233    
3234       /* $ra = $rs << $rb. If count >= 32, then null result */
3235       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
3236       ppc32_op_emit_load_gpr(cpu,X86_ECX,rb);
3237    
3238       iop = ppc32_op_emit_insn_output(cpu,3,"slw");
3239    
3240       x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_t0,hreg_t0);
3241       x86_test_reg_imm(iop->ob_ptr,X86_ECX,0x20);
3242       test1 = iop->ob_ptr;
3243       x86_branch8(iop->ob_ptr, X86_CC_NZ, 0, 1);
3244    
3245       x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_rs,4);
3246       x86_shift_reg(iop->ob_ptr,X86_SHL,hreg_t0);
3247      
3248       /* store the result */
3249       x86_patch(test1,iop->ob_ptr);
3250       x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_t0,4);
3251    
3252     /* Store the result */     if (insn & 1)
3253     x86_patch(test1,b->jit_ptr);        x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
    ppc32_store_gpr(b,ra,X86_EBX);  
3254    
3255     if (insn & 1) {     ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3256        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);    
3257        ppc32_update_cr0(b);     if (insn & 1)
3258     }        ppc32_op_emit_update_flags(cpu,0,TRUE);
3259    
3260       ppc32_jit_close_hreg_seq(cpu);
3261     return(0);     return(0);
3262  }  }
3263    
# Line 1963  DECLARE_INSN(SRAWI) Line 3268  DECLARE_INSN(SRAWI)
3268     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3269     int sh = bits(insn,11,15);     int sh = bits(insn,11,15);
3270     register m_uint32_t mask;     register m_uint32_t mask;
3271       int hreg_rs,hreg_ra,hreg_t0;
3272       jit_op_t *iop;
3273    
3274     mask = ~(0xFFFFFFFFU << sh);     ppc32_jit_start_hreg_seq(cpu,"srawi");
3275       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
3276       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3277       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3278    
3279     /* $ra = (int32)$rs >> sh */     /* $ra = (int32)$rs >> sh */
3280     ppc32_load_gpr(b,X86_EBX,rs);     ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
    x86_mov_reg_reg(b->jit_ptr,X86_ESI,X86_EBX,4);  
    x86_shift_reg_imm(b->jit_ptr,X86_SAR,X86_EBX,sh);  
    ppc32_store_gpr(b,ra,X86_EBX);  
   
    /* test the sign-bit of gpr[rs] */  
    x86_test_reg_reg(b->jit_ptr,X86_ESI,X86_ESI);  
    x86_set_reg(b->jit_ptr,X86_CC_LT,X86_EAX,TRUE);  
   
    x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ESI,mask);  
    x86_set_reg(b->jit_ptr,X86_CC_NZ,X86_ECX,TRUE);  
     
    x86_alu_reg_reg(b->jit_ptr,X86_AND,X86_ECX,X86_EAX);  
    x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_ECX,0x1);  
    x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),X86_ECX,4);  
3281    
3282     if (insn & 1) {     iop = ppc32_op_emit_insn_output(cpu,3,"srawi");
3283        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);     x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_rs,4);
3284        ppc32_update_cr0(b);    
3285     }     if (ra != rs)
3286          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
3287       x86_shift_reg_imm(iop->ob_ptr,X86_SAR,hreg_ra,sh);
3288    
3289       /* set XER_CA depending on the result */
3290       mask = ~(0xFFFFFFFFU << sh) | 0x80000000;
3291    
3292       x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,mask);
3293       x86_alu_reg_imm(iop->ob_ptr,X86_CMP,hreg_t0,0x80000000);
3294       x86_set_reg(iop->ob_ptr,X86_CC_A,hreg_t0,FALSE);
3295       x86_alu_reg_imm(iop->ob_ptr,X86_AND,hreg_t0,0x1);
3296       x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),hreg_t0,4);
3297    
3298       if (insn & 1)
3299          x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
3300    
3301       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3302      
3303       if (insn & 1)
3304          ppc32_op_emit_update_flags(cpu,0,TRUE);
3305    
3306       ppc32_jit_close_hreg_seq(cpu);
3307     return(0);     return(0);
3308  }  }
3309    
# Line 1998  DECLARE_INSN(SRW) Line 3314  DECLARE_INSN(SRW)
3314     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3315     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3316     u_char *test1;     u_char *test1;
3317       int hreg_rs,hreg_ra,hreg_t0;
3318       jit_op_t *iop;
3319    
3320     /* If count >= 32, then null result */     /* ecx is directly modified: throw it */
3321     ppc32_load_gpr(b,X86_ECX,rb);     ppc32_op_emit_alter_host_reg(cpu,X86_ECX);
    x86_alu_reg_reg(b->jit_ptr,X86_XOR,X86_EBX,X86_EBX);  
   
    x86_test_reg_imm(b->jit_ptr,X86_ECX,0x20);  
    test1 = b->jit_ptr;  
    x86_branch8(b->jit_ptr, X86_CC_NZ, 0, 1);  
3322    
3323     ppc32_load_gpr(b,X86_EBX,rs);     ppc32_jit_start_hreg_seq(cpu,"srw");
3324     x86_shift_reg(b->jit_ptr,X86_SHR,X86_EBX);     ppc32_jit_alloc_hreg_forced(cpu,X86_ECX);
3325       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
3326       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3327       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3328    
3329       /* $ra = $rs >> $rb. If count >= 32, then null result */
3330       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
3331       ppc32_op_emit_load_gpr(cpu,X86_ECX,rb);
3332    
3333       iop = ppc32_op_emit_insn_output(cpu,3,"srw");
3334    
3335       x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_t0,hreg_t0);
3336       x86_test_reg_imm(iop->ob_ptr,X86_ECX,0x20);
3337       test1 = iop->ob_ptr;
3338       x86_branch8(iop->ob_ptr, X86_CC_NZ, 0, 1);
3339    
3340       x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_rs,4);
3341       x86_shift_reg(iop->ob_ptr,X86_SHR,hreg_t0);
3342      
3343       /* store the result */
3344       x86_patch(test1,iop->ob_ptr);
3345       x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_t0,4);
3346    
3347     /* Store the result */     if (insn & 1)
3348     x86_patch(test1,b->jit_ptr);        x86_test_reg_reg(iop->ob_ptr,hreg_ra,hreg_ra);
    ppc32_store_gpr(b,ra,X86_EBX);  
3349    
3350     if (insn & 1) {     ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3351        x86_test_reg_reg(b->jit_ptr,X86_EBX,X86_EBX);    
3352        ppc32_update_cr0(b);     if (insn & 1)
3353     }        ppc32_op_emit_update_flags(cpu,0,TRUE);
3354            
3355       ppc32_jit_close_hreg_seq(cpu);
3356     return(0);     return(0);
3357  }  }
3358    
# Line 2030  DECLARE_INSN(STB) Line 3364  DECLARE_INSN(STB)
3364     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
3365    
3366     //ppc32_emit_memop(b,PPC_MEMOP_STB,ra,offset,rs,0);     //ppc32_emit_memop(b,PPC_MEMOP_STB,ra,offset,rs,0);
3367     ppc32_emit_memop_fast(b,1,PPC_MEMOP_STB,ra,offset,rs,ppc32_memop_fast_stb);     ppc32_emit_memop_fast(cpu,b,1,PPC_MEMOP_STB,ra,offset,rs,
3368                             ppc32_memop_fast_stb);
3369     return(0);     return(0);
3370  }  }
3371    
# Line 2041  DECLARE_INSN(STBU) Line 3376  DECLARE_INSN(STBU)
3376     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3377     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
3378    
3379     ppc32_emit_memop(b,PPC_MEMOP_STB,ra,offset,rs,1);     ppc32_emit_memop(cpu,b,PPC_MEMOP_STB,ra,offset,rs,1);
3380     return(0);     return(0);
3381  }  }
3382    
# Line 2052  DECLARE_INSN(STBUX) Line 3387  DECLARE_INSN(STBUX)
3387     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3388     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3389    
3390     ppc32_emit_memop_idx(b,PPC_MEMOP_STB,ra,rb,rs,1);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_STB,ra,rb,rs,1);
3391     return(0);     return(0);
3392  }  }
3393    
# Line 2063  DECLARE_INSN(STBX) Line 3398  DECLARE_INSN(STBX)
3398     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3399     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3400    
3401     ppc32_emit_memop_idx(b,PPC_MEMOP_STB,ra,rb,rs,0);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_STB,ra,rb,rs,0);
3402     return(0);     return(0);
3403  }  }
3404    
# Line 2074  DECLARE_INSN(STH) Line 3409  DECLARE_INSN(STH)
3409     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3410     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
3411    
3412     ppc32_emit_memop(b,PPC_MEMOP_STH,ra,offset,rs,0);     ppc32_emit_memop(cpu,b,PPC_MEMOP_STH,ra,offset,rs,0);
3413     return(0);     return(0);
3414  }  }
3415    
# Line 2085  DECLARE_INSN(STHU) Line 3420  DECLARE_INSN(STHU)
3420     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3421     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
3422    
3423     ppc32_emit_memop(b,PPC_MEMOP_STH,ra,offset,rs,1);     ppc32_emit_memop(cpu,b,PPC_MEMOP_STH,ra,offset,rs,1);
3424     return(0);     return(0);
3425  }  }
3426    
# Line 2096  DECLARE_INSN(STHUX) Line 3431  DECLARE_INSN(STHUX)
3431     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3432     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3433    
3434     ppc32_emit_memop_idx(b,PPC_MEMOP_STH,ra,rb,rs,1);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_STH,ra,rb,rs,1);
3435     return(0);     return(0);
3436  }  }
3437    
# Line 2107  DECLARE_INSN(STHX) Line 3442  DECLARE_INSN(STHX)
3442     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3443     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3444    
3445     ppc32_emit_memop_idx(b,PPC_MEMOP_STH,ra,rb,rs,0);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_STH,ra,rb,rs,0);
3446     return(0);     return(0);
3447  }  }
3448    
# Line 2119  DECLARE_INSN(STW) Line 3454  DECLARE_INSN(STW)
3454     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
3455    
3456     //ppc32_emit_memop(b,PPC_MEMOP_STW,ra,offset,rs,0);     //ppc32_emit_memop(b,PPC_MEMOP_STW,ra,offset,rs,0);
3457     ppc32_emit_memop_fast(b,1,PPC_MEMOP_STW,ra,offset,rs,ppc32_memop_fast_stw);     ppc32_emit_memop_fast(cpu,b,1,PPC_MEMOP_STW,ra,offset,rs,
3458                             ppc32_memop_fast_stw);
3459     return(0);     return(0);
3460  }  }
3461    
# Line 2130  DECLARE_INSN(STWU) Line 3466  DECLARE_INSN(STWU)
3466     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3467     m_uint16_t offset = bits(insn,0,15);     m_uint16_t offset = bits(insn,0,15);
3468    
3469     ppc32_emit_memop(b,PPC_MEMOP_STW,ra,offset,rs,1);     ppc32_emit_memop(cpu,b,PPC_MEMOP_STW,ra,offset,rs,1);
3470     return(0);     return(0);
3471  }  }
3472    
# Line 2141  DECLARE_INSN(STWUX) Line 3477  DECLARE_INSN(STWUX)
3477     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3478     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3479    
3480     ppc32_emit_memop_idx(b,PPC_MEMOP_STW,ra,rb,rs,1);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_STW,ra,rb,rs,1);
3481     return(0);     return(0);
3482  }  }
3483    
# Line 2152  DECLARE_INSN(STWX) Line 3488  DECLARE_INSN(STWX)
3488     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3489     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3490    
3491     ppc32_emit_memop_idx(b,PPC_MEMOP_STW,ra,rb,rs,0);     ppc32_emit_memop_idx(cpu,b,PPC_MEMOP_STW,ra,rb,rs,0);
3492     return(0);     return(0);
3493  }  }
3494    
# Line 2162  DECLARE_INSN(SUBF) Line 3498  DECLARE_INSN(SUBF)
3498     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
3499     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3500     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3501       int hreg_rd,hreg_ra,hreg_rb,hreg_t0;
3502       jit_op_t *iop;
3503    
3504       /* $rd = $rb - $ra */
3505       ppc32_jit_start_hreg_seq(cpu,"subf");
3506       hreg_t0 = ppc32_jit_get_tmp_hreg(cpu);
3507    
3508       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
3509       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3510       hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
3511    
3512       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
3513       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
3514    
3515       iop = ppc32_op_emit_insn_output(cpu,2,"subf");
3516    
3517       if (rd == rb)
3518          x86_alu_reg_reg(iop->ob_ptr,X86_SUB,hreg_rd,hreg_ra);
3519       else if (rd == ra) {
3520          x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_rb,4);
3521          x86_alu_reg_reg(iop->ob_ptr,X86_SUB,hreg_t0,hreg_ra);
3522          x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_t0,4);
3523       } else {
3524          x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_rb,4);
3525          x86_alu_reg_reg(iop->ob_ptr,X86_SUB,hreg_rd,hreg_ra);
3526       }
3527    
3528     /* $rd = $rb - $rb */     ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
    ppc32_load_gpr(b,X86_EBX,rb);  
    ppc32_alu_gpr(b,X86_SUB,X86_EBX,ra);  
    ppc32_store_gpr(b,rd,X86_EBX);  
3529    
3530     if (insn & 1)     if (insn & 1)
3531        ppc32_update_cr0(b);        ppc32_op_emit_update_flags(cpu,0,TRUE);
3532          
3533       ppc32_jit_close_hreg_seq(cpu);
3534     return(0);     return(0);
3535  }  }
3536    
# Line 2180  DECLARE_INSN(SUBFC) Line 3540  DECLARE_INSN(SUBFC)
3540     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
3541     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3542     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3543       int hreg_ra,hreg_rb,hreg_rd,hreg_t0,hreg_t1;
3544       jit_op_t *iop;
3545    
3546     /* ~$ra + 1 */     /* $rd = ~$ra + 1 + $rb */
3547     ppc32_load_gpr(b,X86_ESI,ra);     ppc32_jit_start_hreg_seq(cpu,"subfc");
3548     x86_not_reg(b->jit_ptr,X86_ESI);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3549     x86_alu_reg_imm(b->jit_ptr,X86_ADD,X86_ESI,1);     hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
3550     x86_set_reg(b->jit_ptr,X86_CC_C,X86_EAX,FALSE);     hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
3551    
3552     /* add $rb */     hreg_t0 = ppc32_jit_alloc_hreg(cpu,-1);
3553     ppc32_alu_gpr(b,X86_ADD,X86_ESI,rb);     hreg_t1 = ppc32_jit_get_tmp_hreg(cpu);
3554     x86_set_reg(b->jit_ptr,X86_CC_C,X86_ECX,FALSE);  
3555       ppc32_op_emit_alter_host_reg(cpu,hreg_t0);
3556       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
3557       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
3558    
3559       iop = ppc32_op_emit_insn_output(cpu,3,"subfc");
3560    
3561       x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_t1,hreg_t1);
3562    
3563       /* $t0 = ~$ra + 1 */
3564       x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_ra,4);
3565       x86_not_reg(iop->ob_ptr,hreg_t0);
3566       x86_alu_reg_imm(iop->ob_ptr,X86_ADD,hreg_t0,1);
3567       x86_set_reg(iop->ob_ptr,X86_CC_C,hreg_t1,FALSE);
3568       x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),hreg_t1,4);
3569    
3570       /* $t0 += $rb */
3571       x86_alu_reg_reg(iop->ob_ptr,X86_ADD,hreg_t0,hreg_rb);
3572       x86_set_reg(iop->ob_ptr,X86_CC_C,hreg_t1,FALSE);
3573       x86_alu_membase_reg(iop->ob_ptr,X86_OR,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),
3574                           hreg_t1);
3575    
3576     ppc32_store_gpr(b,rd,X86_ESI);     x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_t0,4);
3577    
3578     /* store the carry flag */     if (insn & 1)
3579     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EAX,X86_ECX);        x86_test_reg_reg(iop->ob_ptr,hreg_rd,hreg_rd);
    x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,0x1);  
3580    
3581     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),X86_EAX,4);     ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
3582    
3583     /* update cr0 */     /* update cr0 */
3584     if (insn & 1) {     if (insn & 1)
       x86_test_reg_reg(b->jit_ptr,X86_ESI,X86_ESI);  
3585        ppc32_update_cr0(b);        ppc32_update_cr0(b);
    }  
3586    
3587       ppc32_jit_close_hreg_seq(cpu);
3588     return(0);     return(0);
3589  }  }
3590    
# Line 2214  DECLARE_INSN(SUBFE) Line 3594  DECLARE_INSN(SUBFE)
3594     int rd = bits(insn,21,25);     int rd = bits(insn,21,25);
3595     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3596     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3597       int hreg_ra,hreg_rb,hreg_rd,hreg_t0,hreg_t1;
3598       jit_op_t *iop;
3599    
3600     /* ~$ra + carry */     /* $rd = ~$ra + $carry (xer_ca) + $rb */
3601     ppc32_load_gpr(b,X86_ESI,ra);     ppc32_jit_start_hreg_seq(cpu,"subfe");
3602     x86_not_reg(b->jit_ptr,X86_ESI);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3603     x86_alu_reg_membase(b->jit_ptr,X86_ADD,X86_ESI,     hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
3604       hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
3605    
3606       hreg_t0 = ppc32_jit_alloc_hreg(cpu,-1);
3607       hreg_t1 = ppc32_jit_get_tmp_hreg(cpu);
3608    
3609       ppc32_op_emit_alter_host_reg(cpu,hreg_t0);
3610       ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
3611       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
3612    
3613       iop = ppc32_op_emit_insn_output(cpu,3,"subfe");
3614    
3615       x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_t1,hreg_t1);
3616    
3617       /* $t0 = ~$ra + $carry */
3618       x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_ra,4);
3619       x86_not_reg(iop->ob_ptr,hreg_t0);
3620       x86_alu_reg_membase(iop->ob_ptr,X86_ADD,hreg_t0,
3621                         X86_EDI,OFFSET(cpu_ppc_t,xer_ca));                         X86_EDI,OFFSET(cpu_ppc_t,xer_ca));
    x86_set_reg(b->jit_ptr,X86_CC_C,X86_EAX,FALSE);  
3622    
3623     /* add $rb */     x86_set_reg(iop->ob_ptr,X86_CC_C,hreg_t1,FALSE);
3624     ppc32_alu_gpr(b,X86_ADD,X86_ESI,rb);     x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),hreg_t1,4);
    x86_set_reg(b->jit_ptr,X86_CC_C,X86_ECX,FALSE);  
3625    
3626     ppc32_store_gpr(b,rd,X86_ESI);     /* $t0 += $rb */
3627       x86_alu_reg_reg(iop->ob_ptr,X86_ADD,hreg_t0,hreg_rb);
3628       x86_set_reg(iop->ob_ptr,X86_CC_C,hreg_t1,FALSE);
3629       x86_alu_membase_reg(iop->ob_ptr,X86_OR,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),
3630                           hreg_t1);
3631    
3632     /* store the carry flag */     x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_t0,4);
3633     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EAX,X86_ECX);  
3634     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,0x1);     if (insn & 1)
3635     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),X86_EAX,4);        x86_test_reg_reg(iop->ob_ptr,hreg_rd,hreg_rd);
3636    
3637       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
3638    
3639     /* update cr0 */     /* update cr0 */
3640     if (insn & 1) {     if (insn & 1)
       x86_test_reg_reg(b->jit_ptr,X86_ESI,X86_ESI);  
3641        ppc32_update_cr0(b);        ppc32_update_cr0(b);
    }  
3642    
3643       ppc32_jit_close_hreg_seq(cpu);
3644     return(0);     return(0);
3645  }  }
3646    
# Line 2249  DECLARE_INSN(SUBFIC) Line 3651  DECLARE_INSN(SUBFIC)
3651     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3652     m_uint16_t imm = bits(insn,0,15);     m_uint16_t imm = bits(insn,0,15);
3653     m_uint32_t tmp = sign_extend_32(imm,16);     m_uint32_t tmp = sign_extend_32(imm,16);
3654       int hreg_ra,hreg_rd,hreg_t0,hreg_t1;
3655       jit_op_t *iop;
3656    
3657     /* ~$ra + 1 */     /* $rd = ~$ra + 1 + sign_extend(imm,16) */
3658     ppc32_load_gpr(b,X86_ESI,ra);     ppc32_jit_start_hreg_seq(cpu,"subfic");
3659     x86_not_reg(b->jit_ptr,X86_ESI);     hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3660     x86_alu_reg_imm(b->jit_ptr,X86_ADD,X86_ESI,1);     hreg_rd = ppc32_jit_alloc_hreg(cpu,rd);
    x86_set_reg(b->jit_ptr,X86_CC_C,X86_EAX,FALSE);  
   
    /* add sign-extended $immediate */  
    x86_alu_reg_imm(b->jit_ptr,X86_ADD,X86_ESI,tmp);  
    x86_set_reg(b->jit_ptr,X86_CC_C,X86_ECX,FALSE);  
3661    
3662     ppc32_store_gpr(b,rd,X86_ESI);     hreg_t0 = ppc32_jit_alloc_hreg(cpu,-1);
3663       hreg_t1 = ppc32_jit_get_tmp_hreg(cpu);
3664    
3665     /* store the carry flag */     ppc32_op_emit_alter_host_reg(cpu,hreg_t0);
3666     x86_alu_reg_reg(b->jit_ptr,X86_OR,X86_EAX,X86_ECX);     ppc32_op_emit_load_gpr(cpu,hreg_ra,ra);
3667     x86_alu_reg_imm(b->jit_ptr,X86_AND,X86_EAX,0x1);  
3668       iop = ppc32_op_emit_insn_output(cpu,3,"subfic");
3669    
3670       x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_t1,hreg_t1);
3671    
3672       /* $t0 = ~$ra + 1 */
3673       x86_mov_reg_reg(iop->ob_ptr,hreg_t0,hreg_ra,4);
3674       x86_not_reg(iop->ob_ptr,hreg_t0);
3675       x86_alu_reg_imm(iop->ob_ptr,X86_ADD,hreg_t0,1);
3676    
3677       x86_set_reg(iop->ob_ptr,X86_CC_C,hreg_t1,FALSE);
3678       x86_mov_membase_reg(iop->ob_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),hreg_t1,4);
3679    
3680     x86_mov_membase_reg(b->jit_ptr,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),X86_EAX,4);     /* $t0 += sign_extend(imm,16) */
3681       x86_alu_reg_imm(iop->ob_ptr,X86_ADD,hreg_t0,tmp);
3682       x86_set_reg(iop->ob_ptr,X86_CC_C,hreg_t1,FALSE);
3683       x86_alu_membase_reg(iop->ob_ptr,X86_OR,X86_EDI,OFFSET(cpu_ppc_t,xer_ca),
3684                           hreg_t1);
3685    
3686       x86_mov_reg_reg(iop->ob_ptr,hreg_rd,hreg_t0,4);
3687       ppc32_op_emit_store_gpr(cpu,rd,hreg_rd);
3688      
3689       ppc32_jit_close_hreg_seq(cpu);
3690     return(0);     return(0);
3691  }  }
3692    
# Line 2282  DECLARE_INSN(XOR) Line 3702  DECLARE_INSN(XOR)
3702     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
3703     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3704     int rb = bits(insn,11,15);     int rb = bits(insn,11,15);
3705       int hreg_rs,hreg_ra,hreg_rb;
3706       jit_op_t *iop;
3707    
3708     ppc32_load_gpr(b,X86_EBX,rs);     /* $ra = $rs ^ $rb */
3709     ppc32_alu_gpr(b,X86_XOR,X86_EBX,rb);     ppc32_jit_start_hreg_seq(cpu,"xor");
3710     ppc32_store_gpr(b,ra,X86_EBX);     hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3711       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3712       hreg_rb = ppc32_jit_alloc_hreg(cpu,rb);
3713    
3714       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
3715       ppc32_op_emit_load_gpr(cpu,hreg_rb,rb);
3716    
3717       iop = ppc32_op_emit_insn_output(cpu,1,"xor");
3718    
3719       if (ra == rs)
3720          x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_ra,hreg_rb);
3721       else if (ra == rb)
3722          x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_ra,hreg_rs);
3723       else {
3724          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
3725          x86_alu_reg_reg(iop->ob_ptr,X86_XOR,hreg_ra,hreg_rb);
3726       }
3727    
3728       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3729    
3730     if (insn & 1)     if (insn & 1)
3731        ppc32_update_cr0(b);        ppc32_op_emit_update_flags(cpu,0,TRUE);
3732    
3733       ppc32_jit_close_hreg_seq(cpu);
3734     return(0);     return(0);
3735  }  }
3736    
# Line 2299  DECLARE_INSN(XORI) Line 3740  DECLARE_INSN(XORI)
3740     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
3741     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3742     m_uint32_t imm = bits(insn,0,15);     m_uint32_t imm = bits(insn,0,15);
3743       int hreg_rs,hreg_ra;
3744       jit_op_t *iop;
3745    
3746       /* $ra = $rs ^ imm */
3747       ppc32_jit_start_hreg_seq(cpu,"xori");
3748       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3749       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3750    
3751       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
3752    
3753       iop = ppc32_op_emit_insn_output(cpu,1,"xori");
3754    
3755       if (ra != rs)
3756          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
3757    
3758     ppc32_load_imm(b,X86_EBX,imm);     x86_alu_reg_imm(iop->ob_ptr,X86_XOR,hreg_ra,imm);
3759     ppc32_alu_gpr(b,X86_XOR,X86_EBX,rs);     ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3760     ppc32_store_gpr(b,ra,X86_EBX);  
3761       ppc32_jit_close_hreg_seq(cpu);
3762     return(0);     return(0);
3763  }  }
3764    
# Line 2311  DECLARE_INSN(XORIS) Line 3767  DECLARE_INSN(XORIS)
3767  {  {
3768     int rs = bits(insn,21,25);     int rs = bits(insn,21,25);
3769     int ra = bits(insn,16,20);     int ra = bits(insn,16,20);
3770     m_uint32_t imm = bits(insn,0,15);     m_uint16_t imm = bits(insn,0,15);
3771       m_uint32_t tmp = imm << 16;
3772       int hreg_rs,hreg_ra;
3773       jit_op_t *iop;
3774    
3775       /* $ra = $rs ^ (imm << 16) */
3776       ppc32_jit_start_hreg_seq(cpu,"xoris");
3777       hreg_rs = ppc32_jit_alloc_hreg(cpu,rs);
3778       hreg_ra = ppc32_jit_alloc_hreg(cpu,ra);
3779    
3780       ppc32_op_emit_load_gpr(cpu,hreg_rs,rs);
3781    
3782       iop = ppc32_op_emit_insn_output(cpu,1,"xoris");
3783    
3784       if (ra != rs)
3785          x86_mov_reg_reg(iop->ob_ptr,hreg_ra,hreg_rs,4);
3786    
3787       x86_alu_reg_imm(iop->ob_ptr,X86_XOR,hreg_ra,tmp);
3788       ppc32_op_emit_store_gpr(cpu,ra,hreg_ra);
3789    
3790     ppc32_load_imm(b,X86_EBX,imm << 16);     ppc32_jit_close_hreg_seq(cpu);
    ppc32_alu_gpr(b,X86_XOR,X86_EBX,rs);  
    ppc32_store_gpr(b,ra,X86_EBX);  
3791     return(0);     return(0);
3792  }  }
3793    
# Line 2336  struct ppc32_insn_tag ppc32_insn_tags[] Line 3808  struct ppc32_insn_tag ppc32_insn_tags[]
3808     { ppc32_emit_ADDIC      , 0xfc000000 , 0x30000000 },     { ppc32_emit_ADDIC      , 0xfc000000 , 0x30000000 },
3809     { ppc32_emit_ADDIC_dot  , 0xfc000000 , 0x34000000 },     { ppc32_emit_ADDIC_dot  , 0xfc000000 , 0x34000000 },
3810     { ppc32_emit_ADDIS      , 0xfc000000 , 0x3c000000 },     { ppc32_emit_ADDIS      , 0xfc000000 , 0x3c000000 },
3811       { ppc32_emit_ADDZE      , 0xfc00fffe , 0x7c000194 },
3812     { ppc32_emit_AND        , 0xfc0007fe , 0x7c000038 },     { ppc32_emit_AND        , 0xfc0007fe , 0x7c000038 },
3813     { ppc32_emit_ANDC       , 0xfc0007fe , 0x7c000078 },     { ppc32_emit_ANDC       , 0xfc0007fe , 0x7c000078 },
3814     { ppc32_emit_ANDI       , 0xfc000000 , 0x70000000 },     { ppc32_emit_ANDI       , 0xfc000000 , 0x70000000 },
# Line 2346  struct ppc32_insn_tag ppc32_insn_tags[] Line 3819  struct ppc32_insn_tag ppc32_insn_tags[]
3819     { ppc32_emit_BLA        , 0xfc000003 , 0x48000003 },     { ppc32_emit_BLA        , 0xfc000003 , 0x48000003 },
3820     { ppc32_emit_BCC        , 0xfe800000 , 0x40800000 },     { ppc32_emit_BCC        , 0xfe800000 , 0x40800000 },
3821     { ppc32_emit_BC         , 0xfc000000 , 0x40000000 },     { ppc32_emit_BC         , 0xfc000000 , 0x40000000 },
3822     { ppc32_emit_BCLR       , 0xfc00fffe , 0x4c000020 },     { ppc32_emit_BCLR       , 0xfc00fffe , 0x4c000020 },  
3823     { ppc32_emit_CMP        , 0xfc6007ff , 0x7c000000 },     { ppc32_emit_CMP        , 0xfc6007ff , 0x7c000000 },
3824     { ppc32_emit_CMPI       , 0xfc600000 , 0x2c000000 },     { ppc32_emit_CMPI       , 0xfc600000 , 0x2c000000 },
3825     { ppc32_emit_CMPL       , 0xfc6007ff , 0x7c000040 },     { ppc32_emit_CMPL       , 0xfc6007ff , 0x7c000040 },
# Line 2422  struct ppc32_insn_tag ppc32_insn_tags[] Line 3895  struct ppc32_insn_tag ppc32_insn_tags[]
3895     { ppc32_emit_XORI       , 0xfc000000 , 0x68000000 },     { ppc32_emit_XORI       , 0xfc000000 , 0x68000000 },
3896     { ppc32_emit_XORIS      , 0xfc000000 , 0x6c000000 },     { ppc32_emit_XORIS      , 0xfc000000 , 0x6c000000 },
3897     { ppc32_emit_unknown    , 0x00000000 , 0x00000000 },     { ppc32_emit_unknown    , 0x00000000 , 0x00000000 },
3898       { NULL                  , 0x00000000 , 0x00000000 },
3899  };  };

Legend:
Removed from v.7  
changed lines
  Added in v.12

  ViewVC Help
Powered by ViewVC 1.1.26