Statistics
| Branch: | Revision:

root / tcg / ppc / tcg-target.c @ a082615b

History | View | Annotate | Download (54.3 kB)

1
/*
2
 * Tiny Code Generator for QEMU
3
 *
4
 * Copyright (c) 2008 Fabrice Bellard
5
 *
6
 * Permission is hereby granted, free of charge, to any person obtaining a copy
7
 * of this software and associated documentation files (the "Software"), to deal
8
 * in the Software without restriction, including without limitation the rights
9
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10
 * copies of the Software, and to permit persons to whom the Software is
11
 * furnished to do so, subject to the following conditions:
12
 *
13
 * The above copyright notice and this permission notice shall be included in
14
 * all copies or substantial portions of the Software.
15
 *
16
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22
 * THE SOFTWARE.
23
 */
24

    
25
static uint8_t *tb_ret_addr;
26

    
27
#ifdef _CALL_DARWIN
28
#define LINKAGE_AREA_SIZE 24
29
#define LR_OFFSET 8
30
#elif defined _CALL_AIX
31
#define LINKAGE_AREA_SIZE 52
32
#define LR_OFFSET 8
33
#else
34
#define LINKAGE_AREA_SIZE 8
35
#define LR_OFFSET 4
36
#endif
37

    
38
#define FAST_PATH
39

    
40
#ifndef GUEST_BASE
41
#define GUEST_BASE 0
42
#endif
43

    
44
#ifdef CONFIG_USE_GUEST_BASE
45
#define TCG_GUEST_BASE_REG 30
46
#else
47
#define TCG_GUEST_BASE_REG 0
48
#endif
49

    
50
#ifndef NDEBUG
51
static const char * const tcg_target_reg_names[TCG_TARGET_NB_REGS] = {
52
    "r0",
53
    "r1",
54
    "r2",
55
    "r3",
56
    "r4",
57
    "r5",
58
    "r6",
59
    "r7",
60
    "r8",
61
    "r9",
62
    "r10",
63
    "r11",
64
    "r12",
65
    "r13",
66
    "r14",
67
    "r15",
68
    "r16",
69
    "r17",
70
    "r18",
71
    "r19",
72
    "r20",
73
    "r21",
74
    "r22",
75
    "r23",
76
    "r24",
77
    "r25",
78
    "r26",
79
    "r27",
80
    "r28",
81
    "r29",
82
    "r30",
83
    "r31"
84
};
85
#endif
86

    
87
static const int tcg_target_reg_alloc_order[] = {
88
    TCG_REG_R14,
89
    TCG_REG_R15,
90
    TCG_REG_R16,
91
    TCG_REG_R17,
92
    TCG_REG_R18,
93
    TCG_REG_R19,
94
    TCG_REG_R20,
95
    TCG_REG_R21,
96
    TCG_REG_R22,
97
    TCG_REG_R23,
98
    TCG_REG_R28,
99
    TCG_REG_R29,
100
    TCG_REG_R30,
101
    TCG_REG_R31,
102
#ifdef _CALL_DARWIN
103
    TCG_REG_R2,
104
#endif
105
    TCG_REG_R3,
106
    TCG_REG_R4,
107
    TCG_REG_R5,
108
    TCG_REG_R6,
109
    TCG_REG_R7,
110
    TCG_REG_R8,
111
    TCG_REG_R9,
112
    TCG_REG_R10,
113
#ifndef _CALL_DARWIN
114
    TCG_REG_R11,
115
#endif
116
    TCG_REG_R12,
117
#ifndef _CALL_SYSV
118
    TCG_REG_R13,
119
#endif
120
    TCG_REG_R24,
121
    TCG_REG_R25,
122
    TCG_REG_R26,
123
    TCG_REG_R27
124
};
125

    
126
static const int tcg_target_call_iarg_regs[] = {
127
    TCG_REG_R3,
128
    TCG_REG_R4,
129
    TCG_REG_R5,
130
    TCG_REG_R6,
131
    TCG_REG_R7,
132
    TCG_REG_R8,
133
    TCG_REG_R9,
134
    TCG_REG_R10
135
};
136

    
137
static const int tcg_target_call_oarg_regs[2] = {
138
    TCG_REG_R3,
139
    TCG_REG_R4
140
};
141

    
142
static const int tcg_target_callee_save_regs[] = {
143
#ifdef _CALL_DARWIN
144
    TCG_REG_R11,
145
    TCG_REG_R13,
146
#endif
147
#ifdef _CALL_AIX
148
    TCG_REG_R13,
149
#endif
150
    TCG_REG_R14,
151
    TCG_REG_R15,
152
    TCG_REG_R16,
153
    TCG_REG_R17,
154
    TCG_REG_R18,
155
    TCG_REG_R19,
156
    TCG_REG_R20,
157
    TCG_REG_R21,
158
    TCG_REG_R22,
159
    TCG_REG_R23,
160
    TCG_REG_R24,
161
    TCG_REG_R25,
162
    TCG_REG_R26,
163
    TCG_REG_R27, /* currently used for the global env */
164
    TCG_REG_R28,
165
    TCG_REG_R29,
166
    TCG_REG_R30,
167
    TCG_REG_R31
168
};
169

    
170
static uint32_t reloc_pc24_val (void *pc, tcg_target_long target)
171
{
172
    tcg_target_long disp;
173

    
174
    disp = target - (tcg_target_long) pc;
175
    if ((disp << 6) >> 6 != disp)
176
        tcg_abort ();
177

    
178
    return disp & 0x3fffffc;
179
}
180

    
181
static void reloc_pc24 (void *pc, tcg_target_long target)
182
{
183
    *(uint32_t *) pc = (*(uint32_t *) pc & ~0x3fffffc)
184
        | reloc_pc24_val (pc, target);
185
}
186

    
187
static uint16_t reloc_pc14_val (void *pc, tcg_target_long target)
188
{
189
    tcg_target_long disp;
190

    
191
    disp = target - (tcg_target_long) pc;
192
    if (disp != (int16_t) disp)
193
        tcg_abort ();
194

    
195
    return disp & 0xfffc;
196
}
197

    
198
static void reloc_pc14 (void *pc, tcg_target_long target)
199
{
200
    *(uint32_t *) pc = (*(uint32_t *) pc & ~0xfffc)
201
        | reloc_pc14_val (pc, target);
202
}
203

    
204
static void patch_reloc(uint8_t *code_ptr, int type,
205
                        tcg_target_long value, tcg_target_long addend)
206
{
207
    value += addend;
208
    switch (type) {
209
    case R_PPC_REL14:
210
        reloc_pc14 (code_ptr, value);
211
        break;
212
    case R_PPC_REL24:
213
        reloc_pc24 (code_ptr, value);
214
        break;
215
    default:
216
        tcg_abort();
217
    }
218
}
219

    
220
/* maximum number of register used for input function arguments */
221
static int tcg_target_get_call_iarg_regs_count(int flags)
222
{
223
    return ARRAY_SIZE (tcg_target_call_iarg_regs);
224
}
225

    
226
/* parse target specific constraints */
227
static int target_parse_constraint(TCGArgConstraint *ct, const char **pct_str)
228
{
229
    const char *ct_str;
230

    
231
    ct_str = *pct_str;
232
    switch (ct_str[0]) {
233
    case 'A': case 'B': case 'C': case 'D':
234
        ct->ct |= TCG_CT_REG;
235
        tcg_regset_set_reg(ct->u.regs, 3 + ct_str[0] - 'A');
236
        break;
237
    case 'r':
238
        ct->ct |= TCG_CT_REG;
239
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
240
        break;
241
#ifdef CONFIG_SOFTMMU
242
    case 'L':                   /* qemu_ld constraint */
243
        ct->ct |= TCG_CT_REG;
244
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
245
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R3);
246
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R4);
247
#if TARGET_LONG_BITS == 64
248
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R5);
249
#endif
250
        break;
251
    case 'K':                   /* qemu_st[8..32] constraint */
252
        ct->ct |= TCG_CT_REG;
253
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
254
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R3);
255
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R4);
256
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R5);
257
#if TARGET_LONG_BITS == 64
258
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R6);
259
#endif
260
        break;
261
    case 'M':                   /* qemu_st64 constraint */
262
        ct->ct |= TCG_CT_REG;
263
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
264
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R3);
265
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R4);
266
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R5);
267
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R6);
268
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R7);
269
        break;
270
#else
271
    case 'L':
272
    case 'K':
273
        ct->ct |= TCG_CT_REG;
274
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
275
        break;
276
    case 'M':
277
        ct->ct |= TCG_CT_REG;
278
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
279
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R3);
280
        break;
281
#endif
282
    default:
283
        return -1;
284
    }
285
    ct_str++;
286
    *pct_str = ct_str;
287
    return 0;
288
}
289

    
290
/* test if a constant matches the constraint */
291
static int tcg_target_const_match(tcg_target_long val,
292
                                  const TCGArgConstraint *arg_ct)
293
{
294
    int ct;
295

    
296
    ct = arg_ct->ct;
297
    if (ct & TCG_CT_CONST)
298
        return 1;
299
    return 0;
300
}
301

    
302
#define OPCD(opc) ((opc)<<26)
303
#define XO31(opc) (OPCD(31)|((opc)<<1))
304
#define XO19(opc) (OPCD(19)|((opc)<<1))
305

    
306
#define B      OPCD(18)
307
#define BC     OPCD(16)
308
#define LBZ    OPCD(34)
309
#define LHZ    OPCD(40)
310
#define LHA    OPCD(42)
311
#define LWZ    OPCD(32)
312
#define STB    OPCD(38)
313
#define STH    OPCD(44)
314
#define STW    OPCD(36)
315

    
316
#define ADDIC  OPCD(12)
317
#define ADDI   OPCD(14)
318
#define ADDIS  OPCD(15)
319
#define ORI    OPCD(24)
320
#define ORIS   OPCD(25)
321
#define XORI   OPCD(26)
322
#define XORIS  OPCD(27)
323
#define ANDI   OPCD(28)
324
#define ANDIS  OPCD(29)
325
#define MULLI  OPCD( 7)
326
#define CMPLI  OPCD(10)
327
#define CMPI   OPCD(11)
328
#define SUBFIC OPCD( 8)
329

    
330
#define LWZU   OPCD(33)
331
#define STWU   OPCD(37)
332

    
333
#define RLWIMI OPCD(20)
334
#define RLWINM OPCD(21)
335
#define RLWNM  OPCD(23)
336

    
337
#define BCLR   XO19( 16)
338
#define BCCTR  XO19(528)
339
#define CRAND  XO19(257)
340
#define CRANDC XO19(129)
341
#define CRNAND XO19(225)
342
#define CROR   XO19(449)
343
#define CRNOR  XO19( 33)
344

    
345
#define EXTSB  XO31(954)
346
#define EXTSH  XO31(922)
347
#define ADD    XO31(266)
348
#define ADDE   XO31(138)
349
#define ADDC   XO31( 10)
350
#define AND    XO31( 28)
351
#define SUBF   XO31( 40)
352
#define SUBFC  XO31(  8)
353
#define SUBFE  XO31(136)
354
#define OR     XO31(444)
355
#define XOR    XO31(316)
356
#define MULLW  XO31(235)
357
#define MULHWU XO31( 11)
358
#define DIVW   XO31(491)
359
#define DIVWU  XO31(459)
360
#define CMP    XO31(  0)
361
#define CMPL   XO31( 32)
362
#define LHBRX  XO31(790)
363
#define LWBRX  XO31(534)
364
#define STHBRX XO31(918)
365
#define STWBRX XO31(662)
366
#define MFSPR  XO31(339)
367
#define MTSPR  XO31(467)
368
#define SRAWI  XO31(824)
369
#define NEG    XO31(104)
370
#define MFCR   XO31( 19)
371
#define CNTLZW XO31( 26)
372
#define NOR    XO31(124)
373
#define ANDC   XO31( 60)
374
#define ORC    XO31(412)
375
#define EQV    XO31(284)
376
#define NAND   XO31(476)
377

    
378
#define LBZX   XO31( 87)
379
#define LHZX   XO31(279)
380
#define LHAX   XO31(343)
381
#define LWZX   XO31( 23)
382
#define STBX   XO31(215)
383
#define STHX   XO31(407)
384
#define STWX   XO31(151)
385

    
386
#define SPR(a,b) ((((a)<<5)|(b))<<11)
387
#define LR     SPR(8, 0)
388
#define CTR    SPR(9, 0)
389

    
390
#define SLW    XO31( 24)
391
#define SRW    XO31(536)
392
#define SRAW   XO31(792)
393

    
394
#define TW     XO31(4)
395
#define TRAP   (TW | TO (31))
396

    
397
#define RT(r) ((r)<<21)
398
#define RS(r) ((r)<<21)
399
#define RA(r) ((r)<<16)
400
#define RB(r) ((r)<<11)
401
#define TO(t) ((t)<<21)
402
#define SH(s) ((s)<<11)
403
#define MB(b) ((b)<<6)
404
#define ME(e) ((e)<<1)
405
#define BO(o) ((o)<<21)
406

    
407
#define LK    1
408

    
409
#define TAB(t,a,b) (RT(t) | RA(a) | RB(b))
410
#define SAB(s,a,b) (RS(s) | RA(a) | RB(b))
411

    
412
#define BF(n)    ((n)<<23)
413
#define BI(n, c) (((c)+((n)*4))<<16)
414
#define BT(n, c) (((c)+((n)*4))<<21)
415
#define BA(n, c) (((c)+((n)*4))<<16)
416
#define BB(n, c) (((c)+((n)*4))<<11)
417

    
418
#define BO_COND_TRUE  BO (12)
419
#define BO_COND_FALSE BO (4)
420
#define BO_ALWAYS     BO (20)
421

    
422
enum {
423
    CR_LT,
424
    CR_GT,
425
    CR_EQ,
426
    CR_SO
427
};
428

    
429
static const uint32_t tcg_to_bc[10] = {
430
    [TCG_COND_EQ]  = BC | BI (7, CR_EQ) | BO_COND_TRUE,
431
    [TCG_COND_NE]  = BC | BI (7, CR_EQ) | BO_COND_FALSE,
432
    [TCG_COND_LT]  = BC | BI (7, CR_LT) | BO_COND_TRUE,
433
    [TCG_COND_GE]  = BC | BI (7, CR_LT) | BO_COND_FALSE,
434
    [TCG_COND_LE]  = BC | BI (7, CR_GT) | BO_COND_FALSE,
435
    [TCG_COND_GT]  = BC | BI (7, CR_GT) | BO_COND_TRUE,
436
    [TCG_COND_LTU] = BC | BI (7, CR_LT) | BO_COND_TRUE,
437
    [TCG_COND_GEU] = BC | BI (7, CR_LT) | BO_COND_FALSE,
438
    [TCG_COND_LEU] = BC | BI (7, CR_GT) | BO_COND_FALSE,
439
    [TCG_COND_GTU] = BC | BI (7, CR_GT) | BO_COND_TRUE,
440
};
441

    
442
static void tcg_out_mov(TCGContext *s, TCGType type, TCGReg ret, TCGReg arg)
443
{
444
    tcg_out32 (s, OR | SAB (arg, ret, arg));
445
}
446

    
447
static void tcg_out_movi(TCGContext *s, TCGType type,
448
                         TCGReg ret, tcg_target_long arg)
449
{
450
    if (arg == (int16_t) arg)
451
        tcg_out32 (s, ADDI | RT (ret) | RA (0) | (arg & 0xffff));
452
    else {
453
        tcg_out32 (s, ADDIS | RT (ret) | RA (0) | ((arg >> 16) & 0xffff));
454
        if (arg & 0xffff)
455
            tcg_out32 (s, ORI | RS (ret) | RA (ret) | (arg & 0xffff));
456
    }
457
}
458

    
459
static void tcg_out_ldst (TCGContext *s, int ret, int addr,
460
                          int offset, int op1, int op2)
461
{
462
    if (offset == (int16_t) offset)
463
        tcg_out32 (s, op1 | RT (ret) | RA (addr) | (offset & 0xffff));
464
    else {
465
        tcg_out_movi (s, TCG_TYPE_I32, 0, offset);
466
        tcg_out32 (s, op2 | RT (ret) | RA (addr) | RB (0));
467
    }
468
}
469

    
470
static void tcg_out_b (TCGContext *s, int mask, tcg_target_long target)
471
{
472
    tcg_target_long disp;
473

    
474
    disp = target - (tcg_target_long) s->code_ptr;
475
    if ((disp << 6) >> 6 == disp)
476
        tcg_out32 (s, B | (disp & 0x3fffffc) | mask);
477
    else {
478
        tcg_out_movi (s, TCG_TYPE_I32, 0, (tcg_target_long) target);
479
        tcg_out32 (s, MTSPR | RS (0) | CTR);
480
        tcg_out32 (s, BCCTR | BO_ALWAYS | mask);
481
    }
482
}
483

    
484
static void tcg_out_call (TCGContext *s, tcg_target_long arg, int const_arg)
485
{
486
#ifdef _CALL_AIX
487
    int reg;
488

    
489
    if (const_arg) {
490
        reg = 2;
491
        tcg_out_movi (s, TCG_TYPE_I32, reg, arg);
492
    }
493
    else reg = arg;
494

    
495
    tcg_out32 (s, LWZ | RT (0) | RA (reg));
496
    tcg_out32 (s, MTSPR | RA (0) | CTR);
497
    tcg_out32 (s, LWZ | RT (2) | RA (reg) | 4);
498
    tcg_out32 (s, BCCTR | BO_ALWAYS | LK);
499
#else
500
    if (const_arg) {
501
        tcg_out_b (s, LK, arg);
502
    }
503
    else {
504
        tcg_out32 (s, MTSPR | RS (arg) | LR);
505
        tcg_out32 (s, BCLR | BO_ALWAYS | LK);
506
    }
507
#endif
508
}
509

    
510
#if defined(CONFIG_SOFTMMU)
511

    
512
#include "../../softmmu_defs.h"
513

    
514
#ifdef CONFIG_TCG_PASS_AREG0
515
#error CONFIG_TCG_PASS_AREG0 is not supported
516
/* helper signature: helper_ld_mmu(CPUState *env, target_ulong addr,
517
   int mmu_idx) */
518
static const void * const qemu_ld_helpers[4] = {
519
    helper_ldb_mmu,
520
    helper_ldw_mmu,
521
    helper_ldl_mmu,
522
    helper_ldq_mmu,
523
};
524

    
525
/* helper signature: helper_st_mmu(CPUState *env, target_ulong addr,
526
   uintxx_t val, int mmu_idx) */
527
static const void * const qemu_st_helpers[4] = {
528
    helper_stb_mmu,
529
    helper_stw_mmu,
530
    helper_stl_mmu,
531
    helper_stq_mmu,
532
};
533
#else
534
/* legacy helper signature: __ld_mmu(target_ulong addr, int
535
   mmu_idx) */
536
static void *qemu_ld_helpers[4] = {
537
    __ldb_mmu,
538
    __ldw_mmu,
539
    __ldl_mmu,
540
    __ldq_mmu,
541
};
542

    
543
/* legacy helper signature: __ld_mmu(target_ulong addr, int
544
   mmu_idx) */
545
static void *qemu_st_helpers[4] = {
546
    __stb_mmu,
547
    __stw_mmu,
548
    __stl_mmu,
549
    __stq_mmu,
550
};
551
#endif
552
#endif
553

    
554
static void tcg_out_qemu_ld (TCGContext *s, const TCGArg *args, int opc)
555
{
556
    int addr_reg, data_reg, data_reg2, r0, r1, rbase, bswap;
557
#ifdef CONFIG_SOFTMMU
558
    int mem_index, s_bits, r2, ir;
559
    void *label1_ptr, *label2_ptr;
560
#if TARGET_LONG_BITS == 64
561
    int addr_reg2;
562
#endif
563
#endif
564

    
565
    data_reg = *args++;
566
    if (opc == 3)
567
        data_reg2 = *args++;
568
    else
569
        data_reg2 = 0;
570
    addr_reg = *args++;
571

    
572
#ifdef CONFIG_SOFTMMU
573
#if TARGET_LONG_BITS == 64
574
    addr_reg2 = *args++;
575
#endif
576
    mem_index = *args;
577
    s_bits = opc & 3;
578
    r0 = 3;
579
    r1 = 4;
580
    r2 = 0;
581
    rbase = 0;
582

    
583
    tcg_out32 (s, (RLWINM
584
                   | RA (r0)
585
                   | RS (addr_reg)
586
                   | SH (32 - (TARGET_PAGE_BITS - CPU_TLB_ENTRY_BITS))
587
                   | MB (32 - (CPU_TLB_BITS + CPU_TLB_ENTRY_BITS))
588
                   | ME (31 - CPU_TLB_ENTRY_BITS)
589
                   )
590
        );
591
    tcg_out32 (s, ADD | RT (r0) | RA (r0) | RB (TCG_AREG0));
592
    tcg_out32 (s, (LWZU
593
                   | RT (r1)
594
                   | RA (r0)
595
                   | offsetof (CPUArchState, tlb_table[mem_index][0].addr_read)
596
                   )
597
        );
598
    tcg_out32 (s, (RLWINM
599
                   | RA (r2)
600
                   | RS (addr_reg)
601
                   | SH (0)
602
                   | MB ((32 - s_bits) & 31)
603
                   | ME (31 - TARGET_PAGE_BITS)
604
                   )
605
        );
606

    
607
    tcg_out32 (s, CMP | BF (7) | RA (r2) | RB (r1));
608
#if TARGET_LONG_BITS == 64
609
    tcg_out32 (s, LWZ | RT (r1) | RA (r0) | 4);
610
    tcg_out32 (s, CMP | BF (6) | RA (addr_reg2) | RB (r1));
611
    tcg_out32 (s, CRAND | BT (7, CR_EQ) | BA (6, CR_EQ) | BB (7, CR_EQ));
612
#endif
613

    
614
    label1_ptr = s->code_ptr;
615
#ifdef FAST_PATH
616
    tcg_out32 (s, BC | BI (7, CR_EQ) | BO_COND_TRUE);
617
#endif
618

    
619
    /* slow path */
620
    ir = 3;
621
#if TARGET_LONG_BITS == 32
622
    tcg_out_mov (s, TCG_TYPE_I32, ir++, addr_reg);
623
#else
624
#ifdef TCG_TARGET_CALL_ALIGN_ARGS
625
    ir |= 1;
626
#endif
627
    tcg_out_mov (s, TCG_TYPE_I32, ir++, addr_reg2);
628
    tcg_out_mov (s, TCG_TYPE_I32, ir++, addr_reg);
629
#endif
630
    tcg_out_movi (s, TCG_TYPE_I32, ir, mem_index);
631

    
632
    tcg_out_call (s, (tcg_target_long) qemu_ld_helpers[s_bits], 1);
633
    switch (opc) {
634
    case 0|4:
635
        tcg_out32 (s, EXTSB | RA (data_reg) | RS (3));
636
        break;
637
    case 1|4:
638
        tcg_out32 (s, EXTSH | RA (data_reg) | RS (3));
639
        break;
640
    case 0:
641
    case 1:
642
    case 2:
643
        if (data_reg != 3)
644
            tcg_out_mov (s, TCG_TYPE_I32, data_reg, 3);
645
        break;
646
    case 3:
647
        if (data_reg == 3) {
648
            if (data_reg2 == 4) {
649
                tcg_out_mov (s, TCG_TYPE_I32, 0, 4);
650
                tcg_out_mov (s, TCG_TYPE_I32, 4, 3);
651
                tcg_out_mov (s, TCG_TYPE_I32, 3, 0);
652
            }
653
            else {
654
                tcg_out_mov (s, TCG_TYPE_I32, data_reg2, 3);
655
                tcg_out_mov (s, TCG_TYPE_I32, 3, 4);
656
            }
657
        }
658
        else {
659
            if (data_reg != 4) tcg_out_mov (s, TCG_TYPE_I32, data_reg, 4);
660
            if (data_reg2 != 3) tcg_out_mov (s, TCG_TYPE_I32, data_reg2, 3);
661
        }
662
        break;
663
    }
664
    label2_ptr = s->code_ptr;
665
    tcg_out32 (s, B);
666

    
667
    /* label1: fast path */
668
#ifdef FAST_PATH
669
    reloc_pc14 (label1_ptr, (tcg_target_long) s->code_ptr);
670
#endif
671

    
672
    /* r0 now contains &env->tlb_table[mem_index][index].addr_read */
673
    tcg_out32 (s, (LWZ
674
                   | RT (r0)
675
                   | RA (r0)
676
                   | (offsetof (CPUTLBEntry, addend)
677
                      - offsetof (CPUTLBEntry, addr_read))
678
                   ));
679
    /* r0 = env->tlb_table[mem_index][index].addend */
680
    tcg_out32 (s, ADD | RT (r0) | RA (r0) | RB (addr_reg));
681
    /* r0 = env->tlb_table[mem_index][index].addend + addr */
682

    
683
#else  /* !CONFIG_SOFTMMU */
684
    r0 = addr_reg;
685
    r1 = 3;
686
    rbase = GUEST_BASE ? TCG_GUEST_BASE_REG : 0;
687
#endif
688

    
689
#ifdef TARGET_WORDS_BIGENDIAN
690
    bswap = 0;
691
#else
692
    bswap = 1;
693
#endif
694

    
695
    switch (opc) {
696
    default:
697
    case 0:
698
        tcg_out32 (s, LBZX | TAB (data_reg, rbase, r0));
699
        break;
700
    case 0|4:
701
        tcg_out32 (s, LBZX | TAB (data_reg, rbase, r0));
702
        tcg_out32 (s, EXTSB | RA (data_reg) | RS (data_reg));
703
        break;
704
    case 1:
705
        if (bswap)
706
            tcg_out32 (s, LHBRX | TAB (data_reg, rbase, r0));
707
        else
708
            tcg_out32 (s, LHZX | TAB (data_reg, rbase, r0));
709
        break;
710
    case 1|4:
711
        if (bswap) {
712
            tcg_out32 (s, LHBRX | TAB (data_reg, rbase, r0));
713
            tcg_out32 (s, EXTSH | RA (data_reg) | RS (data_reg));
714
        }
715
        else tcg_out32 (s, LHAX | TAB (data_reg, rbase, r0));
716
        break;
717
    case 2:
718
        if (bswap)
719
            tcg_out32 (s, LWBRX | TAB (data_reg, rbase, r0));
720
        else
721
            tcg_out32 (s, LWZX | TAB (data_reg, rbase, r0));
722
        break;
723
    case 3:
724
        if (bswap) {
725
            tcg_out32 (s, ADDI | RT (r1) | RA (r0) | 4);
726
            tcg_out32 (s, LWBRX | TAB (data_reg, rbase, r0));
727
            tcg_out32 (s, LWBRX | TAB (data_reg2, rbase, r1));
728
        }
729
        else {
730
#ifdef CONFIG_USE_GUEST_BASE
731
            tcg_out32 (s, ADDI | RT (r1) | RA (r0) | 4);
732
            tcg_out32 (s, LWZX | TAB (data_reg2, rbase, r0));
733
            tcg_out32 (s, LWZX | TAB (data_reg, rbase, r1));
734
#else
735
            if (r0 == data_reg2) {
736
                tcg_out32 (s, LWZ | RT (0) | RA (r0));
737
                tcg_out32 (s, LWZ | RT (data_reg) | RA (r0) | 4);
738
                tcg_out_mov (s, TCG_TYPE_I32, data_reg2, 0);
739
            }
740
            else {
741
                tcg_out32 (s, LWZ | RT (data_reg2) | RA (r0));
742
                tcg_out32 (s, LWZ | RT (data_reg) | RA (r0) | 4);
743
            }
744
#endif
745
        }
746
        break;
747
    }
748

    
749
#ifdef CONFIG_SOFTMMU
750
    reloc_pc24 (label2_ptr, (tcg_target_long) s->code_ptr);
751
#endif
752
}
753

    
754
static void tcg_out_qemu_st (TCGContext *s, const TCGArg *args, int opc)
755
{
756
    int addr_reg, r0, r1, data_reg, data_reg2, bswap, rbase;
757
#ifdef CONFIG_SOFTMMU
758
    int mem_index, r2, ir;
759
    void *label1_ptr, *label2_ptr;
760
#if TARGET_LONG_BITS == 64
761
    int addr_reg2;
762
#endif
763
#endif
764

    
765
    data_reg = *args++;
766
    if (opc == 3)
767
        data_reg2 = *args++;
768
    else
769
        data_reg2 = 0;
770
    addr_reg = *args++;
771

    
772
#ifdef CONFIG_SOFTMMU
773
#if TARGET_LONG_BITS == 64
774
    addr_reg2 = *args++;
775
#endif
776
    mem_index = *args;
777
    r0 = 3;
778
    r1 = 4;
779
    r2 = 0;
780
    rbase = 0;
781

    
782
    tcg_out32 (s, (RLWINM
783
                   | RA (r0)
784
                   | RS (addr_reg)
785
                   | SH (32 - (TARGET_PAGE_BITS - CPU_TLB_ENTRY_BITS))
786
                   | MB (32 - (CPU_TLB_ENTRY_BITS + CPU_TLB_BITS))
787
                   | ME (31 - CPU_TLB_ENTRY_BITS)
788
                   )
789
        );
790
    tcg_out32 (s, ADD | RT (r0) | RA (r0) | RB (TCG_AREG0));
791
    tcg_out32 (s, (LWZU
792
                   | RT (r1)
793
                   | RA (r0)
794
                   | offsetof (CPUArchState, tlb_table[mem_index][0].addr_write)
795
                   )
796
        );
797
    tcg_out32 (s, (RLWINM
798
                   | RA (r2)
799
                   | RS (addr_reg)
800
                   | SH (0)
801
                   | MB ((32 - opc) & 31)
802
                   | ME (31 - TARGET_PAGE_BITS)
803
                   )
804
        );
805

    
806
    tcg_out32 (s, CMP | (7 << 23) | RA (r2) | RB (r1));
807
#if TARGET_LONG_BITS == 64
808
    tcg_out32 (s, LWZ | RT (r1) | RA (r0) | 4);
809
    tcg_out32 (s, CMP | BF (6) | RA (addr_reg2) | RB (r1));
810
    tcg_out32 (s, CRAND | BT (7, CR_EQ) | BA (6, CR_EQ) | BB (7, CR_EQ));
811
#endif
812

    
813
    label1_ptr = s->code_ptr;
814
#ifdef FAST_PATH
815
    tcg_out32 (s, BC | BI (7, CR_EQ) | BO_COND_TRUE);
816
#endif
817

    
818
    /* slow path */
819
    ir = 3;
820
#if TARGET_LONG_BITS == 32
821
    tcg_out_mov (s, TCG_TYPE_I32, ir++, addr_reg);
822
#else
823
#ifdef TCG_TARGET_CALL_ALIGN_ARGS
824
    ir |= 1;
825
#endif
826
    tcg_out_mov (s, TCG_TYPE_I32, ir++, addr_reg2);
827
    tcg_out_mov (s, TCG_TYPE_I32, ir++, addr_reg);
828
#endif
829

    
830
    switch (opc) {
831
    case 0:
832
        tcg_out32 (s, (RLWINM
833
                       | RA (ir)
834
                       | RS (data_reg)
835
                       | SH (0)
836
                       | MB (24)
837
                       | ME (31)));
838
        break;
839
    case 1:
840
        tcg_out32 (s, (RLWINM
841
                       | RA (ir)
842
                       | RS (data_reg)
843
                       | SH (0)
844
                       | MB (16)
845
                       | ME (31)));
846
        break;
847
    case 2:
848
        tcg_out_mov (s, TCG_TYPE_I32, ir, data_reg);
849
        break;
850
    case 3:
851
#ifdef TCG_TARGET_CALL_ALIGN_ARGS
852
        ir |= 1;
853
#endif
854
        tcg_out_mov (s, TCG_TYPE_I32, ir++, data_reg2);
855
        tcg_out_mov (s, TCG_TYPE_I32, ir, data_reg);
856
        break;
857
    }
858
    ir++;
859

    
860
    tcg_out_movi (s, TCG_TYPE_I32, ir, mem_index);
861
    tcg_out_call (s, (tcg_target_long) qemu_st_helpers[opc], 1);
862
    label2_ptr = s->code_ptr;
863
    tcg_out32 (s, B);
864

    
865
    /* label1: fast path */
866
#ifdef FAST_PATH
867
    reloc_pc14 (label1_ptr, (tcg_target_long) s->code_ptr);
868
#endif
869

    
870
    tcg_out32 (s, (LWZ
871
                   | RT (r0)
872
                   | RA (r0)
873
                   | (offsetof (CPUTLBEntry, addend)
874
                      - offsetof (CPUTLBEntry, addr_write))
875
                   ));
876
    /* r0 = env->tlb_table[mem_index][index].addend */
877
    tcg_out32 (s, ADD | RT (r0) | RA (r0) | RB (addr_reg));
878
    /* r0 = env->tlb_table[mem_index][index].addend + addr */
879

    
880
#else  /* !CONFIG_SOFTMMU */
881
    r0 = addr_reg;
882
    r1 = 3;
883
    rbase = GUEST_BASE ? TCG_GUEST_BASE_REG : 0;
884
#endif
885

    
886
#ifdef TARGET_WORDS_BIGENDIAN
887
    bswap = 0;
888
#else
889
    bswap = 1;
890
#endif
891
    switch (opc) {
892
    case 0:
893
        tcg_out32 (s, STBX | SAB (data_reg, rbase, r0));
894
        break;
895
    case 1:
896
        if (bswap)
897
            tcg_out32 (s, STHBRX | SAB (data_reg, rbase, r0));
898
        else
899
            tcg_out32 (s, STHX | SAB (data_reg, rbase, r0));
900
        break;
901
    case 2:
902
        if (bswap)
903
            tcg_out32 (s, STWBRX | SAB (data_reg, rbase, r0));
904
        else
905
            tcg_out32 (s, STWX | SAB (data_reg, rbase, r0));
906
        break;
907
    case 3:
908
        if (bswap) {
909
            tcg_out32 (s, ADDI | RT (r1) | RA (r0) | 4);
910
            tcg_out32 (s, STWBRX | SAB (data_reg,  rbase, r0));
911
            tcg_out32 (s, STWBRX | SAB (data_reg2, rbase, r1));
912
        }
913
        else {
914
#ifdef CONFIG_USE_GUEST_BASE
915
            tcg_out32 (s, STWX | SAB (data_reg2, rbase, r0));
916
            tcg_out32 (s, ADDI | RT (r1) | RA (r0) | 4);
917
            tcg_out32 (s, STWX | SAB (data_reg,  rbase, r1));
918
#else
919
            tcg_out32 (s, STW | RS (data_reg2) | RA (r0));
920
            tcg_out32 (s, STW | RS (data_reg) | RA (r0) | 4);
921
#endif
922
        }
923
        break;
924
    }
925

    
926
#ifdef CONFIG_SOFTMMU
927
    reloc_pc24 (label2_ptr, (tcg_target_long) s->code_ptr);
928
#endif
929
}
930

    
931
static void tcg_target_qemu_prologue (TCGContext *s)
932
{
933
    int i, frame_size;
934

    
935
    frame_size = 0
936
        + LINKAGE_AREA_SIZE
937
        + TCG_STATIC_CALL_ARGS_SIZE
938
        + ARRAY_SIZE (tcg_target_callee_save_regs) * 4
939
        + CPU_TEMP_BUF_NLONGS * sizeof(long)
940
        ;
941
    frame_size = (frame_size + 15) & ~15;
942

    
943
    tcg_set_frame(s, TCG_REG_CALL_STACK, frame_size
944
                  - CPU_TEMP_BUF_NLONGS * sizeof(long),
945
                  CPU_TEMP_BUF_NLONGS * sizeof(long));
946

    
947
#ifdef _CALL_AIX
948
    {
949
        uint32_t addr;
950

    
951
        /* First emit adhoc function descriptor */
952
        addr = (uint32_t) s->code_ptr + 12;
953
        tcg_out32 (s, addr);        /* entry point */
954
        s->code_ptr += 8;           /* skip TOC and environment pointer */
955
    }
956
#endif
957
    tcg_out32 (s, MFSPR | RT (0) | LR);
958
    tcg_out32 (s, STWU | RS (1) | RA (1) | (-frame_size & 0xffff));
959
    for (i = 0; i < ARRAY_SIZE (tcg_target_callee_save_regs); ++i)
960
        tcg_out32 (s, (STW
961
                       | RS (tcg_target_callee_save_regs[i])
962
                       | RA (1)
963
                       | (i * 4 + LINKAGE_AREA_SIZE + TCG_STATIC_CALL_ARGS_SIZE)
964
                       )
965
            );
966
    tcg_out32 (s, STW | RS (0) | RA (1) | (frame_size + LR_OFFSET));
967

    
968
#ifdef CONFIG_USE_GUEST_BASE
969
    if (GUEST_BASE) {
970
        tcg_out_movi (s, TCG_TYPE_I32, TCG_GUEST_BASE_REG, GUEST_BASE);
971
        tcg_regset_set_reg(s->reserved_regs, TCG_GUEST_BASE_REG);
972
    }
973
#endif
974

    
975
    tcg_out_mov (s, TCG_TYPE_PTR, TCG_AREG0, tcg_target_call_iarg_regs[0]);
976
    tcg_out32 (s, MTSPR | RS (tcg_target_call_iarg_regs[1]) | CTR);
977
    tcg_out32 (s, BCCTR | BO_ALWAYS);
978
    tb_ret_addr = s->code_ptr;
979

    
980
    for (i = 0; i < ARRAY_SIZE (tcg_target_callee_save_regs); ++i)
981
        tcg_out32 (s, (LWZ
982
                       | RT (tcg_target_callee_save_regs[i])
983
                       | RA (1)
984
                       | (i * 4 + LINKAGE_AREA_SIZE + TCG_STATIC_CALL_ARGS_SIZE)
985
                       )
986
            );
987
    tcg_out32 (s, LWZ | RT (0) | RA (1) | (frame_size + LR_OFFSET));
988
    tcg_out32 (s, MTSPR | RS (0) | LR);
989
    tcg_out32 (s, ADDI | RT (1) | RA (1) | frame_size);
990
    tcg_out32 (s, BCLR | BO_ALWAYS);
991
}
992

    
993
static void tcg_out_ld (TCGContext *s, TCGType type, TCGReg ret, TCGReg arg1,
994
                        tcg_target_long arg2)
995
{
996
    tcg_out_ldst (s, ret, arg1, arg2, LWZ, LWZX);
997
}
998

    
999
static void tcg_out_st (TCGContext *s, TCGType type, TCGReg arg, TCGReg arg1,
1000
                        tcg_target_long arg2)
1001
{
1002
    tcg_out_ldst (s, arg, arg1, arg2, STW, STWX);
1003
}
1004

    
1005
static void ppc_addi (TCGContext *s, int rt, int ra, tcg_target_long si)
1006
{
1007
    if (!si && rt == ra)
1008
        return;
1009

    
1010
    if (si == (int16_t) si)
1011
        tcg_out32 (s, ADDI | RT (rt) | RA (ra) | (si & 0xffff));
1012
    else {
1013
        uint16_t h = ((si >> 16) & 0xffff) + ((uint16_t) si >> 15);
1014
        tcg_out32 (s, ADDIS | RT (rt) | RA (ra) | h);
1015
        tcg_out32 (s, ADDI | RT (rt) | RA (rt) | (si & 0xffff));
1016
    }
1017
}
1018

    
1019
static void tcg_out_cmp (TCGContext *s, int cond, TCGArg arg1, TCGArg arg2,
1020
                         int const_arg2, int cr)
1021
{
1022
    int imm;
1023
    uint32_t op;
1024

    
1025
    switch (cond) {
1026
    case TCG_COND_EQ:
1027
    case TCG_COND_NE:
1028
        if (const_arg2) {
1029
            if ((int16_t) arg2 == arg2) {
1030
                op = CMPI;
1031
                imm = 1;
1032
                break;
1033
            }
1034
            else if ((uint16_t) arg2 == arg2) {
1035
                op = CMPLI;
1036
                imm = 1;
1037
                break;
1038
            }
1039
        }
1040
        op = CMPL;
1041
        imm = 0;
1042
        break;
1043

    
1044
    case TCG_COND_LT:
1045
    case TCG_COND_GE:
1046
    case TCG_COND_LE:
1047
    case TCG_COND_GT:
1048
        if (const_arg2) {
1049
            if ((int16_t) arg2 == arg2) {
1050
                op = CMPI;
1051
                imm = 1;
1052
                break;
1053
            }
1054
        }
1055
        op = CMP;
1056
        imm = 0;
1057
        break;
1058

    
1059
    case TCG_COND_LTU:
1060
    case TCG_COND_GEU:
1061
    case TCG_COND_LEU:
1062
    case TCG_COND_GTU:
1063
        if (const_arg2) {
1064
            if ((uint16_t) arg2 == arg2) {
1065
                op = CMPLI;
1066
                imm = 1;
1067
                break;
1068
            }
1069
        }
1070
        op = CMPL;
1071
        imm = 0;
1072
        break;
1073

    
1074
    default:
1075
        tcg_abort ();
1076
    }
1077
    op |= BF (cr);
1078

    
1079
    if (imm)
1080
        tcg_out32 (s, op | RA (arg1) | (arg2 & 0xffff));
1081
    else {
1082
        if (const_arg2) {
1083
            tcg_out_movi (s, TCG_TYPE_I32, 0, arg2);
1084
            tcg_out32 (s, op | RA (arg1) | RB (0));
1085
        }
1086
        else
1087
            tcg_out32 (s, op | RA (arg1) | RB (arg2));
1088
    }
1089

    
1090
}
1091

    
1092
static void tcg_out_bc (TCGContext *s, int bc, int label_index)
1093
{
1094
    TCGLabel *l = &s->labels[label_index];
1095

    
1096
    if (l->has_value)
1097
        tcg_out32 (s, bc | reloc_pc14_val (s->code_ptr, l->u.value));
1098
    else {
1099
        uint16_t val = *(uint16_t *) &s->code_ptr[2];
1100

    
1101
        /* Thanks to Andrzej Zaborowski */
1102
        tcg_out32 (s, bc | (val & 0xfffc));
1103
        tcg_out_reloc (s, s->code_ptr - 4, R_PPC_REL14, label_index, 0);
1104
    }
1105
}
1106

    
1107
static void tcg_out_cr7eq_from_cond (TCGContext *s, const TCGArg *args,
1108
                                     const int *const_args)
1109
{
1110
    TCGCond cond = args[4];
1111
    int op;
1112
    struct { int bit1; int bit2; int cond2; } bits[] = {
1113
        [TCG_COND_LT ] = { CR_LT, CR_LT, TCG_COND_LT  },
1114
        [TCG_COND_LE ] = { CR_LT, CR_GT, TCG_COND_LT  },
1115
        [TCG_COND_GT ] = { CR_GT, CR_GT, TCG_COND_GT  },
1116
        [TCG_COND_GE ] = { CR_GT, CR_LT, TCG_COND_GT  },
1117
        [TCG_COND_LTU] = { CR_LT, CR_LT, TCG_COND_LTU },
1118
        [TCG_COND_LEU] = { CR_LT, CR_GT, TCG_COND_LTU },
1119
        [TCG_COND_GTU] = { CR_GT, CR_GT, TCG_COND_GTU },
1120
        [TCG_COND_GEU] = { CR_GT, CR_LT, TCG_COND_GTU },
1121
    }, *b = &bits[cond];
1122

    
1123
    switch (cond) {
1124
    case TCG_COND_EQ:
1125
    case TCG_COND_NE:
1126
        op = (cond == TCG_COND_EQ) ? CRAND : CRNAND;
1127
        tcg_out_cmp (s, cond, args[0], args[2], const_args[2], 6);
1128
        tcg_out_cmp (s, cond, args[1], args[3], const_args[3], 7);
1129
        tcg_out32 (s, op | BT (7, CR_EQ) | BA (6, CR_EQ) | BB (7, CR_EQ));
1130
        break;
1131
    case TCG_COND_LT:
1132
    case TCG_COND_LE:
1133
    case TCG_COND_GT:
1134
    case TCG_COND_GE:
1135
    case TCG_COND_LTU:
1136
    case TCG_COND_LEU:
1137
    case TCG_COND_GTU:
1138
    case TCG_COND_GEU:
1139
        op = (b->bit1 != b->bit2) ? CRANDC : CRAND;
1140
        tcg_out_cmp (s, b->cond2, args[1], args[3], const_args[3], 5);
1141
        tcg_out_cmp (s, tcg_unsigned_cond (cond), args[0], args[2],
1142
                     const_args[2], 7);
1143
        tcg_out32 (s, op | BT (7, CR_EQ) | BA (5, CR_EQ) | BB (7, b->bit2));
1144
        tcg_out32 (s, CROR | BT (7, CR_EQ) | BA (5, b->bit1) | BB (7, CR_EQ));
1145
        break;
1146
    default:
1147
        tcg_abort();
1148
    }
1149
}
1150

    
1151
static void tcg_out_setcond (TCGContext *s, TCGCond cond, TCGArg arg0,
1152
                             TCGArg arg1, TCGArg arg2, int const_arg2)
1153
{
1154
    int crop, sh, arg;
1155

    
1156
    switch (cond) {
1157
    case TCG_COND_EQ:
1158
        if (const_arg2) {
1159
            if (!arg2) {
1160
                arg = arg1;
1161
            }
1162
            else {
1163
                arg = 0;
1164
                if ((uint16_t) arg2 == arg2) {
1165
                    tcg_out32 (s, XORI | RS (arg1) | RA (0) | arg2);
1166
                }
1167
                else {
1168
                    tcg_out_movi (s, TCG_TYPE_I32, 0, arg2);
1169
                    tcg_out32 (s, XOR | SAB (arg1, 0, 0));
1170
                }
1171
            }
1172
        }
1173
        else {
1174
            arg = 0;
1175
            tcg_out32 (s, XOR | SAB (arg1, 0, arg2));
1176
        }
1177
        tcg_out32 (s, CNTLZW | RS (arg) | RA (0));
1178
        tcg_out32 (s, (RLWINM
1179
                       | RA (arg0)
1180
                       | RS (0)
1181
                       | SH (27)
1182
                       | MB (5)
1183
                       | ME (31)
1184
                       )
1185
            );
1186
        break;
1187

    
1188
    case TCG_COND_NE:
1189
        if (const_arg2) {
1190
            if (!arg2) {
1191
                arg = arg1;
1192
            }
1193
            else {
1194
                arg = 0;
1195
                if ((uint16_t) arg2 == arg2) {
1196
                    tcg_out32 (s, XORI | RS (arg1) | RA (0) | arg2);
1197
                }
1198
                else {
1199
                    tcg_out_movi (s, TCG_TYPE_I32, 0, arg2);
1200
                    tcg_out32 (s, XOR | SAB (arg1, 0, 0));
1201
                }
1202
            }
1203
        }
1204
        else {
1205
            arg = 0;
1206
            tcg_out32 (s, XOR | SAB (arg1, 0, arg2));
1207
        }
1208

    
1209
        if (arg == arg1 && arg1 == arg0) {
1210
            tcg_out32 (s, ADDIC | RT (0) | RA (arg) | 0xffff);
1211
            tcg_out32 (s, SUBFE | TAB (arg0, 0, arg));
1212
        }
1213
        else {
1214
            tcg_out32 (s, ADDIC | RT (arg0) | RA (arg) | 0xffff);
1215
            tcg_out32 (s, SUBFE | TAB (arg0, arg0, arg));
1216
        }
1217
        break;
1218

    
1219
    case TCG_COND_GT:
1220
    case TCG_COND_GTU:
1221
        sh = 30;
1222
        crop = 0;
1223
        goto crtest;
1224

    
1225
    case TCG_COND_LT:
1226
    case TCG_COND_LTU:
1227
        sh = 29;
1228
        crop = 0;
1229
        goto crtest;
1230

    
1231
    case TCG_COND_GE:
1232
    case TCG_COND_GEU:
1233
        sh = 31;
1234
        crop = CRNOR | BT (7, CR_EQ) | BA (7, CR_LT) | BB (7, CR_LT);
1235
        goto crtest;
1236

    
1237
    case TCG_COND_LE:
1238
    case TCG_COND_LEU:
1239
        sh = 31;
1240
        crop = CRNOR | BT (7, CR_EQ) | BA (7, CR_GT) | BB (7, CR_GT);
1241
    crtest:
1242
        tcg_out_cmp (s, cond, arg1, arg2, const_arg2, 7);
1243
        if (crop) tcg_out32 (s, crop);
1244
        tcg_out32 (s, MFCR | RT (0));
1245
        tcg_out32 (s, (RLWINM
1246
                       | RA (arg0)
1247
                       | RS (0)
1248
                       | SH (sh)
1249
                       | MB (31)
1250
                       | ME (31)
1251
                       )
1252
            );
1253
        break;
1254

    
1255
    default:
1256
        tcg_abort ();
1257
    }
1258
}
1259

    
1260
static void tcg_out_setcond2 (TCGContext *s, const TCGArg *args,
1261
                              const int *const_args)
1262
{
1263
    tcg_out_cr7eq_from_cond (s, args + 1, const_args + 1);
1264
    tcg_out32 (s, MFCR | RT (0));
1265
    tcg_out32 (s, (RLWINM
1266
                   | RA (args[0])
1267
                   | RS (0)
1268
                   | SH (31)
1269
                   | MB (31)
1270
                   | ME (31)
1271
                   )
1272
        );
1273
}
1274

    
1275
static void tcg_out_brcond (TCGContext *s, TCGCond cond,
1276
                            TCGArg arg1, TCGArg arg2, int const_arg2,
1277
                            int label_index)
1278
{
1279
    tcg_out_cmp (s, cond, arg1, arg2, const_arg2, 7);
1280
    tcg_out_bc (s, tcg_to_bc[cond], label_index);
1281
}
1282

    
1283
/* XXX: we implement it at the target level to avoid having to
1284
   handle cross basic blocks temporaries */
1285
static void tcg_out_brcond2 (TCGContext *s, const TCGArg *args,
1286
                             const int *const_args)
1287
{
1288
    tcg_out_cr7eq_from_cond (s, args, const_args);
1289
    tcg_out_bc (s, (BC | BI (7, CR_EQ) | BO_COND_TRUE), args[5]);
1290
}
1291

    
1292
void ppc_tb_set_jmp_target (unsigned long jmp_addr, unsigned long addr)
1293
{
1294
    uint32_t *ptr;
1295
    long disp = addr - jmp_addr;
1296
    unsigned long patch_size;
1297

    
1298
    ptr = (uint32_t *)jmp_addr;
1299

    
1300
    if ((disp << 6) >> 6 != disp) {
1301
        ptr[0] = 0x3c000000 | (addr >> 16);    /* lis 0,addr@ha */
1302
        ptr[1] = 0x60000000 | (addr & 0xffff); /* la  0,addr@l(0) */
1303
        ptr[2] = 0x7c0903a6;                   /* mtctr 0 */
1304
        ptr[3] = 0x4e800420;                   /* brctr */
1305
        patch_size = 16;
1306
    } else {
1307
        /* patch the branch destination */
1308
        if (disp != 16) {
1309
            *ptr = 0x48000000 | (disp & 0x03fffffc); /* b disp */
1310
            patch_size = 4;
1311
        } else {
1312
            ptr[0] = 0x60000000; /* nop */
1313
            ptr[1] = 0x60000000;
1314
            ptr[2] = 0x60000000;
1315
            ptr[3] = 0x60000000;
1316
            patch_size = 16;
1317
        }
1318
    }
1319
    /* flush icache */
1320
    flush_icache_range(jmp_addr, jmp_addr + patch_size);
1321
}
1322

    
1323
static void tcg_out_op(TCGContext *s, TCGOpcode opc, const TCGArg *args,
1324
                       const int *const_args)
1325
{
1326
    switch (opc) {
1327
    case INDEX_op_exit_tb:
1328
        tcg_out_movi (s, TCG_TYPE_I32, TCG_REG_R3, args[0]);
1329
        tcg_out_b (s, 0, (tcg_target_long) tb_ret_addr);
1330
        break;
1331
    case INDEX_op_goto_tb:
1332
        if (s->tb_jmp_offset) {
1333
            /* direct jump method */
1334

    
1335
            s->tb_jmp_offset[args[0]] = s->code_ptr - s->code_buf;
1336
            s->code_ptr += 16;
1337
        }
1338
        else {
1339
            tcg_abort ();
1340
        }
1341
        s->tb_next_offset[args[0]] = s->code_ptr - s->code_buf;
1342
        break;
1343
    case INDEX_op_br:
1344
        {
1345
            TCGLabel *l = &s->labels[args[0]];
1346

    
1347
            if (l->has_value) {
1348
                tcg_out_b (s, 0, l->u.value);
1349
            }
1350
            else {
1351
                uint32_t val = *(uint32_t *) s->code_ptr;
1352

    
1353
                /* Thanks to Andrzej Zaborowski */
1354
                tcg_out32 (s, B | (val & 0x3fffffc));
1355
                tcg_out_reloc (s, s->code_ptr - 4, R_PPC_REL24, args[0], 0);
1356
            }
1357
        }
1358
        break;
1359
    case INDEX_op_call:
1360
        tcg_out_call (s, args[0], const_args[0]);
1361
        break;
1362
    case INDEX_op_jmp:
1363
        if (const_args[0]) {
1364
            tcg_out_b (s, 0, args[0]);
1365
        }
1366
        else {
1367
            tcg_out32 (s, MTSPR | RS (args[0]) | CTR);
1368
            tcg_out32 (s, BCCTR | BO_ALWAYS);
1369
        }
1370
        break;
1371
    case INDEX_op_movi_i32:
1372
        tcg_out_movi(s, TCG_TYPE_I32, args[0], args[1]);
1373
        break;
1374
    case INDEX_op_ld8u_i32:
1375
        tcg_out_ldst (s, args[0], args[1], args[2], LBZ, LBZX);
1376
        break;
1377
    case INDEX_op_ld8s_i32:
1378
        tcg_out_ldst (s, args[0], args[1], args[2], LBZ, LBZX);
1379
        tcg_out32 (s, EXTSB | RS (args[0]) | RA (args[0]));
1380
        break;
1381
    case INDEX_op_ld16u_i32:
1382
        tcg_out_ldst (s, args[0], args[1], args[2], LHZ, LHZX);
1383
        break;
1384
    case INDEX_op_ld16s_i32:
1385
        tcg_out_ldst (s, args[0], args[1], args[2], LHA, LHAX);
1386
        break;
1387
    case INDEX_op_ld_i32:
1388
        tcg_out_ldst (s, args[0], args[1], args[2], LWZ, LWZX);
1389
        break;
1390
    case INDEX_op_st8_i32:
1391
        tcg_out_ldst (s, args[0], args[1], args[2], STB, STBX);
1392
        break;
1393
    case INDEX_op_st16_i32:
1394
        tcg_out_ldst (s, args[0], args[1], args[2], STH, STHX);
1395
        break;
1396
    case INDEX_op_st_i32:
1397
        tcg_out_ldst (s, args[0], args[1], args[2], STW, STWX);
1398
        break;
1399

    
1400
    case INDEX_op_add_i32:
1401
        if (const_args[2])
1402
            ppc_addi (s, args[0], args[1], args[2]);
1403
        else
1404
            tcg_out32 (s, ADD | TAB (args[0], args[1], args[2]));
1405
        break;
1406
    case INDEX_op_sub_i32:
1407
        if (const_args[2])
1408
            ppc_addi (s, args[0], args[1], -args[2]);
1409
        else
1410
            tcg_out32 (s, SUBF | TAB (args[0], args[2], args[1]));
1411
        break;
1412

    
1413
    case INDEX_op_and_i32:
1414
        if (const_args[2]) {
1415
            uint32_t c;
1416

    
1417
            c = args[2];
1418

    
1419
            if (!c) {
1420
                tcg_out_movi (s, TCG_TYPE_I32, args[0], 0);
1421
                break;
1422
            }
1423
#ifdef __PPU__
1424
            uint32_t t, n;
1425
            int mb, me;
1426

    
1427
            n = c ^ -(c & 1);
1428
            t = n + (n & -n);
1429

    
1430
            if ((t & (t - 1)) == 0) {
1431
                int lzc, tzc;
1432

    
1433
                if ((c & 0x80000001) == 0x80000001) {
1434
                    lzc = clz32 (n);
1435
                    tzc = ctz32 (n);
1436

    
1437
                    mb = 32 - tzc;
1438
                    me = lzc - 1;
1439
                }
1440
                else {
1441
                    lzc = clz32 (c);
1442
                    tzc = ctz32 (c);
1443

    
1444
                    mb = lzc;
1445
                    me = 31 - tzc;
1446
                }
1447

    
1448
                tcg_out32 (s, (RLWINM
1449
                               | RA (args[0])
1450
                               | RS (args[1])
1451
                               | SH (0)
1452
                               | MB (mb)
1453
                               | ME (me)
1454
                               )
1455
                    );
1456
            }
1457
            else
1458
#endif /* !__PPU__ */
1459
            {
1460
                if ((c & 0xffff) == c)
1461
                    tcg_out32 (s, ANDI | RS (args[1]) | RA (args[0]) | c);
1462
                else if ((c & 0xffff0000) == c)
1463
                    tcg_out32 (s, ANDIS | RS (args[1]) | RA (args[0])
1464
                               | ((c >> 16) & 0xffff));
1465
                else {
1466
                    tcg_out_movi (s, TCG_TYPE_I32, 0, c);
1467
                    tcg_out32 (s, AND | SAB (args[1], args[0], 0));
1468
                }
1469
            }
1470
        }
1471
        else
1472
            tcg_out32 (s, AND | SAB (args[1], args[0], args[2]));
1473
        break;
1474
    case INDEX_op_or_i32:
1475
        if (const_args[2]) {
1476
            if (args[2] & 0xffff) {
1477
                tcg_out32 (s, ORI | RS (args[1])  | RA (args[0])
1478
                           | (args[2] & 0xffff));
1479
                if (args[2] >> 16)
1480
                    tcg_out32 (s, ORIS | RS (args[0])  | RA (args[0])
1481
                               | ((args[2] >> 16) & 0xffff));
1482
            }
1483
            else {
1484
                tcg_out32 (s, ORIS | RS (args[1])  | RA (args[0])
1485
                           | ((args[2] >> 16) & 0xffff));
1486
            }
1487
        }
1488
        else
1489
            tcg_out32 (s, OR | SAB (args[1], args[0], args[2]));
1490
        break;
1491
    case INDEX_op_xor_i32:
1492
        if (const_args[2]) {
1493
            if ((args[2] & 0xffff) == args[2])
1494
                tcg_out32 (s, XORI | RS (args[1])  | RA (args[0])
1495
                           | (args[2] & 0xffff));
1496
            else if ((args[2] & 0xffff0000) == args[2])
1497
                tcg_out32 (s, XORIS | RS (args[1])  | RA (args[0])
1498
                           | ((args[2] >> 16) & 0xffff));
1499
            else {
1500
                tcg_out_movi (s, TCG_TYPE_I32, 0, args[2]);
1501
                tcg_out32 (s, XOR | SAB (args[1], args[0], 0));
1502
            }
1503
        }
1504
        else
1505
            tcg_out32 (s, XOR | SAB (args[1], args[0], args[2]));
1506
        break;
1507
    case INDEX_op_andc_i32:
1508
        tcg_out32 (s, ANDC | SAB (args[1], args[0], args[2]));
1509
        break;
1510
    case INDEX_op_orc_i32:
1511
        tcg_out32 (s, ORC | SAB (args[1], args[0], args[2]));
1512
        break;
1513
    case INDEX_op_eqv_i32:
1514
        tcg_out32 (s, EQV | SAB (args[1], args[0], args[2]));
1515
        break;
1516
    case INDEX_op_nand_i32:
1517
        tcg_out32 (s, NAND | SAB (args[1], args[0], args[2]));
1518
        break;
1519
    case INDEX_op_nor_i32:
1520
        tcg_out32 (s, NOR | SAB (args[1], args[0], args[2]));
1521
        break;
1522

    
1523
    case INDEX_op_mul_i32:
1524
        if (const_args[2]) {
1525
            if (args[2] == (int16_t) args[2])
1526
                tcg_out32 (s, MULLI | RT (args[0]) | RA (args[1])
1527
                           | (args[2] & 0xffff));
1528
            else {
1529
                tcg_out_movi (s, TCG_TYPE_I32, 0, args[2]);
1530
                tcg_out32 (s, MULLW | TAB (args[0], args[1], 0));
1531
            }
1532
        }
1533
        else
1534
            tcg_out32 (s, MULLW | TAB (args[0], args[1], args[2]));
1535
        break;
1536

    
1537
    case INDEX_op_div_i32:
1538
        tcg_out32 (s, DIVW | TAB (args[0], args[1], args[2]));
1539
        break;
1540

    
1541
    case INDEX_op_divu_i32:
1542
        tcg_out32 (s, DIVWU | TAB (args[0], args[1], args[2]));
1543
        break;
1544

    
1545
    case INDEX_op_rem_i32:
1546
        tcg_out32 (s, DIVW | TAB (0, args[1], args[2]));
1547
        tcg_out32 (s, MULLW | TAB (0, 0, args[2]));
1548
        tcg_out32 (s, SUBF | TAB (args[0], 0, args[1]));
1549
        break;
1550

    
1551
    case INDEX_op_remu_i32:
1552
        tcg_out32 (s, DIVWU | TAB (0, args[1], args[2]));
1553
        tcg_out32 (s, MULLW | TAB (0, 0, args[2]));
1554
        tcg_out32 (s, SUBF | TAB (args[0], 0, args[1]));
1555
        break;
1556

    
1557
    case INDEX_op_mulu2_i32:
1558
        if (args[0] == args[2] || args[0] == args[3]) {
1559
            tcg_out32 (s, MULLW | TAB (0, args[2], args[3]));
1560
            tcg_out32 (s, MULHWU | TAB (args[1], args[2], args[3]));
1561
            tcg_out_mov (s, TCG_TYPE_I32, args[0], 0);
1562
        }
1563
        else {
1564
            tcg_out32 (s, MULLW | TAB (args[0], args[2], args[3]));
1565
            tcg_out32 (s, MULHWU | TAB (args[1], args[2], args[3]));
1566
        }
1567
        break;
1568

    
1569
    case INDEX_op_shl_i32:
1570
        if (const_args[2]) {
1571
            tcg_out32 (s, (RLWINM
1572
                           | RA (args[0])
1573
                           | RS (args[1])
1574
                           | SH (args[2])
1575
                           | MB (0)
1576
                           | ME (31 - args[2])
1577
                           )
1578
                );
1579
        }
1580
        else
1581
            tcg_out32 (s, SLW | SAB (args[1], args[0], args[2]));
1582
        break;
1583
    case INDEX_op_shr_i32:
1584
        if (const_args[2]) {
1585
            tcg_out32 (s, (RLWINM
1586
                           | RA (args[0])
1587
                           | RS (args[1])
1588
                           | SH (32 - args[2])
1589
                           | MB (args[2])
1590
                           | ME (31)
1591
                           )
1592
                );
1593
        }
1594
        else
1595
            tcg_out32 (s, SRW | SAB (args[1], args[0], args[2]));
1596
        break;
1597
    case INDEX_op_sar_i32:
1598
        if (const_args[2])
1599
            tcg_out32 (s, SRAWI | RS (args[1]) | RA (args[0]) | SH (args[2]));
1600
        else
1601
            tcg_out32 (s, SRAW | SAB (args[1], args[0], args[2]));
1602
        break;
1603
    case INDEX_op_rotl_i32:
1604
        {
1605
            int op = 0
1606
                | RA (args[0])
1607
                | RS (args[1])
1608
                | MB (0)
1609
                | ME (31)
1610
                | (const_args[2] ? RLWINM | SH (args[2])
1611
                                 : RLWNM | RB (args[2]))
1612
                ;
1613
            tcg_out32 (s, op);
1614
        }
1615
        break;
1616
    case INDEX_op_rotr_i32:
1617
        if (const_args[2]) {
1618
            if (!args[2]) {
1619
                tcg_out_mov (s, TCG_TYPE_I32, args[0], args[1]);
1620
            }
1621
            else {
1622
                tcg_out32 (s, RLWINM
1623
                           | RA (args[0])
1624
                           | RS (args[1])
1625
                           | SH (32 - args[2])
1626
                           | MB (0)
1627
                           | ME (31)
1628
                    );
1629
            }
1630
        }
1631
        else {
1632
            tcg_out32 (s, SUBFIC | RT (0) | RA (args[2]) | 32);
1633
            tcg_out32 (s, RLWNM
1634
                       | RA (args[0])
1635
                       | RS (args[1])
1636
                       | RB (0)
1637
                       | MB (0)
1638
                       | ME (31)
1639
                );
1640
        }
1641
        break;
1642

    
1643
    case INDEX_op_add2_i32:
1644
        if (args[0] == args[3] || args[0] == args[5]) {
1645
            tcg_out32 (s, ADDC | TAB (0, args[2], args[4]));
1646
            tcg_out32 (s, ADDE | TAB (args[1], args[3], args[5]));
1647
            tcg_out_mov (s, TCG_TYPE_I32, args[0], 0);
1648
        }
1649
        else {
1650
            tcg_out32 (s, ADDC | TAB (args[0], args[2], args[4]));
1651
            tcg_out32 (s, ADDE | TAB (args[1], args[3], args[5]));
1652
        }
1653
        break;
1654
    case INDEX_op_sub2_i32:
1655
        if (args[0] == args[3] || args[0] == args[5]) {
1656
            tcg_out32 (s, SUBFC | TAB (0, args[4], args[2]));
1657
            tcg_out32 (s, SUBFE | TAB (args[1], args[5], args[3]));
1658
            tcg_out_mov (s, TCG_TYPE_I32, args[0], 0);
1659
        }
1660
        else {
1661
            tcg_out32 (s, SUBFC | TAB (args[0], args[4], args[2]));
1662
            tcg_out32 (s, SUBFE | TAB (args[1], args[5], args[3]));
1663
        }
1664
        break;
1665

    
1666
    case INDEX_op_brcond_i32:
1667
        /*
1668
          args[0] = r0
1669
          args[1] = r1
1670
          args[2] = cond
1671
          args[3] = r1 is const
1672
          args[4] = label_index
1673
        */
1674
        tcg_out_brcond (s, args[2], args[0], args[1], const_args[1], args[3]);
1675
        break;
1676
    case INDEX_op_brcond2_i32:
1677
        tcg_out_brcond2(s, args, const_args);
1678
        break;
1679

    
1680
    case INDEX_op_neg_i32:
1681
        tcg_out32 (s, NEG | RT (args[0]) | RA (args[1]));
1682
        break;
1683

    
1684
    case INDEX_op_not_i32:
1685
        tcg_out32 (s, NOR | SAB (args[1], args[0], args[1]));
1686
        break;
1687

    
1688
    case INDEX_op_qemu_ld8u:
1689
        tcg_out_qemu_ld(s, args, 0);
1690
        break;
1691
    case INDEX_op_qemu_ld8s:
1692
        tcg_out_qemu_ld(s, args, 0 | 4);
1693
        break;
1694
    case INDEX_op_qemu_ld16u:
1695
        tcg_out_qemu_ld(s, args, 1);
1696
        break;
1697
    case INDEX_op_qemu_ld16s:
1698
        tcg_out_qemu_ld(s, args, 1 | 4);
1699
        break;
1700
    case INDEX_op_qemu_ld32:
1701
        tcg_out_qemu_ld(s, args, 2);
1702
        break;
1703
    case INDEX_op_qemu_ld64:
1704
        tcg_out_qemu_ld(s, args, 3);
1705
        break;
1706
    case INDEX_op_qemu_st8:
1707
        tcg_out_qemu_st(s, args, 0);
1708
        break;
1709
    case INDEX_op_qemu_st16:
1710
        tcg_out_qemu_st(s, args, 1);
1711
        break;
1712
    case INDEX_op_qemu_st32:
1713
        tcg_out_qemu_st(s, args, 2);
1714
        break;
1715
    case INDEX_op_qemu_st64:
1716
        tcg_out_qemu_st(s, args, 3);
1717
        break;
1718

    
1719
    case INDEX_op_ext8s_i32:
1720
        tcg_out32 (s, EXTSB | RS (args[1]) | RA (args[0]));
1721
        break;
1722
    case INDEX_op_ext8u_i32:
1723
        tcg_out32 (s, RLWINM
1724
                   | RA (args[0])
1725
                   | RS (args[1])
1726
                   | SH (0)
1727
                   | MB (24)
1728
                   | ME (31)
1729
            );
1730
        break;
1731
    case INDEX_op_ext16s_i32:
1732
        tcg_out32 (s, EXTSH | RS (args[1]) | RA (args[0]));
1733
        break;
1734
    case INDEX_op_ext16u_i32:
1735
        tcg_out32 (s, RLWINM
1736
                   | RA (args[0])
1737
                   | RS (args[1])
1738
                   | SH (0)
1739
                   | MB (16)
1740
                   | ME (31)
1741
            );
1742
        break;
1743

    
1744
    case INDEX_op_setcond_i32:
1745
        tcg_out_setcond (s, args[3], args[0], args[1], args[2], const_args[2]);
1746
        break;
1747
    case INDEX_op_setcond2_i32:
1748
        tcg_out_setcond2 (s, args, const_args);
1749
        break;
1750

    
1751
    case INDEX_op_bswap16_i32:
1752
        /* Stolen from gcc's builtin_bswap16 */
1753

    
1754
        /* a1 = abcd */
1755

    
1756
        /* r0 = (a1 << 8) & 0xff00 # 00d0 */
1757
        tcg_out32 (s, RLWINM
1758
                   | RA (0)
1759
                   | RS (args[1])
1760
                   | SH (8)
1761
                   | MB (16)
1762
                   | ME (23)
1763
            );
1764

    
1765
        /* a0 = rotate_left (a1, 24) & 0xff # 000c */
1766
        tcg_out32 (s, RLWINM
1767
                   | RA (args[0])
1768
                   | RS (args[1])
1769
                   | SH (24)
1770
                   | MB (24)
1771
                   | ME (31)
1772
            );
1773

    
1774
        /* a0 = a0 | r0 # 00dc */
1775
        tcg_out32 (s, OR | SAB (0, args[0], args[0]));
1776
        break;
1777

    
1778
    case INDEX_op_bswap32_i32:
1779
        /* Stolen from gcc's builtin_bswap32 */
1780
        {
1781
            int a0 = args[0];
1782

    
1783
            /* a1 = args[1] # abcd */
1784

    
1785
            if (a0 == args[1]) {
1786
                a0 = 0;
1787
            }
1788

    
1789
            /* a0 = rotate_left (a1, 8) # bcda */
1790
            tcg_out32 (s, RLWINM
1791
                       | RA (a0)
1792
                       | RS (args[1])
1793
                       | SH (8)
1794
                       | MB (0)
1795
                       | ME (31)
1796
                );
1797

    
1798
            /* a0 = (a0 & ~0xff000000) | ((a1 << 24) & 0xff000000) # dcda */
1799
            tcg_out32 (s, RLWIMI
1800
                       | RA (a0)
1801
                       | RS (args[1])
1802
                       | SH (24)
1803
                       | MB (0)
1804
                       | ME (7)
1805
                );
1806

    
1807
            /* a0 = (a0 & ~0x0000ff00) | ((a1 << 24) & 0x0000ff00) # dcba */
1808
            tcg_out32 (s, RLWIMI
1809
                       | RA (a0)
1810
                       | RS (args[1])
1811
                       | SH (24)
1812
                       | MB (16)
1813
                       | ME (23)
1814
                );
1815

    
1816
            if (!a0) {
1817
                tcg_out_mov (s, TCG_TYPE_I32, args[0], a0);
1818
            }
1819
        }
1820
        break;
1821

    
1822
    case INDEX_op_deposit_i32:
1823
        tcg_out32 (s, RLWIMI
1824
                   | RA (args[0])
1825
                   | RS (args[2])
1826
                   | SH (args[3])
1827
                   | MB (32 - args[3] - args[4])
1828
                   | ME (31 - args[3])
1829
            );
1830
        break;
1831

    
1832
    default:
1833
        tcg_dump_ops (s, stderr);
1834
        tcg_abort ();
1835
    }
1836
}
1837

    
1838
static const TCGTargetOpDef ppc_op_defs[] = {
1839
    { INDEX_op_exit_tb, { } },
1840
    { INDEX_op_goto_tb, { } },
1841
    { INDEX_op_call, { "ri" } },
1842
    { INDEX_op_jmp, { "ri" } },
1843
    { INDEX_op_br, { } },
1844

    
1845
    { INDEX_op_mov_i32, { "r", "r" } },
1846
    { INDEX_op_movi_i32, { "r" } },
1847
    { INDEX_op_ld8u_i32, { "r", "r" } },
1848
    { INDEX_op_ld8s_i32, { "r", "r" } },
1849
    { INDEX_op_ld16u_i32, { "r", "r" } },
1850
    { INDEX_op_ld16s_i32, { "r", "r" } },
1851
    { INDEX_op_ld_i32, { "r", "r" } },
1852
    { INDEX_op_st8_i32, { "r", "r" } },
1853
    { INDEX_op_st16_i32, { "r", "r" } },
1854
    { INDEX_op_st_i32, { "r", "r" } },
1855

    
1856
    { INDEX_op_add_i32, { "r", "r", "ri" } },
1857
    { INDEX_op_mul_i32, { "r", "r", "ri" } },
1858
    { INDEX_op_div_i32, { "r", "r", "r" } },
1859
    { INDEX_op_divu_i32, { "r", "r", "r" } },
1860
    { INDEX_op_rem_i32, { "r", "r", "r" } },
1861
    { INDEX_op_remu_i32, { "r", "r", "r" } },
1862
    { INDEX_op_mulu2_i32, { "r", "r", "r", "r" } },
1863
    { INDEX_op_sub_i32, { "r", "r", "ri" } },
1864
    { INDEX_op_and_i32, { "r", "r", "ri" } },
1865
    { INDEX_op_or_i32, { "r", "r", "ri" } },
1866
    { INDEX_op_xor_i32, { "r", "r", "ri" } },
1867

    
1868
    { INDEX_op_shl_i32, { "r", "r", "ri" } },
1869
    { INDEX_op_shr_i32, { "r", "r", "ri" } },
1870
    { INDEX_op_sar_i32, { "r", "r", "ri" } },
1871

    
1872
    { INDEX_op_rotl_i32, { "r", "r", "ri" } },
1873
    { INDEX_op_rotr_i32, { "r", "r", "ri" } },
1874

    
1875
    { INDEX_op_brcond_i32, { "r", "ri" } },
1876

    
1877
    { INDEX_op_add2_i32, { "r", "r", "r", "r", "r", "r" } },
1878
    { INDEX_op_sub2_i32, { "r", "r", "r", "r", "r", "r" } },
1879
    { INDEX_op_brcond2_i32, { "r", "r", "r", "r" } },
1880

    
1881
    { INDEX_op_neg_i32, { "r", "r" } },
1882
    { INDEX_op_not_i32, { "r", "r" } },
1883

    
1884
    { INDEX_op_andc_i32, { "r", "r", "r" } },
1885
    { INDEX_op_orc_i32, { "r", "r", "r" } },
1886
    { INDEX_op_eqv_i32, { "r", "r", "r" } },
1887
    { INDEX_op_nand_i32, { "r", "r", "r" } },
1888
    { INDEX_op_nor_i32, { "r", "r", "r" } },
1889

    
1890
    { INDEX_op_setcond_i32, { "r", "r", "ri" } },
1891
    { INDEX_op_setcond2_i32, { "r", "r", "r", "ri", "ri" } },
1892

    
1893
    { INDEX_op_bswap16_i32, { "r", "r" } },
1894
    { INDEX_op_bswap32_i32, { "r", "r" } },
1895

    
1896
#if TARGET_LONG_BITS == 32
1897
    { INDEX_op_qemu_ld8u, { "r", "L" } },
1898
    { INDEX_op_qemu_ld8s, { "r", "L" } },
1899
    { INDEX_op_qemu_ld16u, { "r", "L" } },
1900
    { INDEX_op_qemu_ld16s, { "r", "L" } },
1901
    { INDEX_op_qemu_ld32, { "r", "L" } },
1902
    { INDEX_op_qemu_ld64, { "r", "r", "L" } },
1903

    
1904
    { INDEX_op_qemu_st8, { "K", "K" } },
1905
    { INDEX_op_qemu_st16, { "K", "K" } },
1906
    { INDEX_op_qemu_st32, { "K", "K" } },
1907
    { INDEX_op_qemu_st64, { "M", "M", "M" } },
1908
#else
1909
    { INDEX_op_qemu_ld8u, { "r", "L", "L" } },
1910
    { INDEX_op_qemu_ld8s, { "r", "L", "L" } },
1911
    { INDEX_op_qemu_ld16u, { "r", "L", "L" } },
1912
    { INDEX_op_qemu_ld16s, { "r", "L", "L" } },
1913
    { INDEX_op_qemu_ld32, { "r", "L", "L" } },
1914
    { INDEX_op_qemu_ld64, { "r", "L", "L", "L" } },
1915

    
1916
    { INDEX_op_qemu_st8, { "K", "K", "K" } },
1917
    { INDEX_op_qemu_st16, { "K", "K", "K" } },
1918
    { INDEX_op_qemu_st32, { "K", "K", "K" } },
1919
    { INDEX_op_qemu_st64, { "M", "M", "M", "M" } },
1920
#endif
1921

    
1922
    { INDEX_op_ext8s_i32, { "r", "r" } },
1923
    { INDEX_op_ext8u_i32, { "r", "r" } },
1924
    { INDEX_op_ext16s_i32, { "r", "r" } },
1925
    { INDEX_op_ext16u_i32, { "r", "r" } },
1926

    
1927
    { INDEX_op_deposit_i32, { "r", "0", "r" } },
1928

    
1929
    { -1 },
1930
};
1931

    
1932
static void tcg_target_init(TCGContext *s)
1933
{
1934
    tcg_regset_set32(tcg_target_available_regs[TCG_TYPE_I32], 0, 0xffffffff);
1935
    tcg_regset_set32(tcg_target_call_clobber_regs, 0,
1936
                     (1 << TCG_REG_R0) |
1937
#ifdef _CALL_DARWIN
1938
                     (1 << TCG_REG_R2) |
1939
#endif
1940
                     (1 << TCG_REG_R3) |
1941
                     (1 << TCG_REG_R4) |
1942
                     (1 << TCG_REG_R5) |
1943
                     (1 << TCG_REG_R6) |
1944
                     (1 << TCG_REG_R7) |
1945
                     (1 << TCG_REG_R8) |
1946
                     (1 << TCG_REG_R9) |
1947
                     (1 << TCG_REG_R10) |
1948
                     (1 << TCG_REG_R11) |
1949
                     (1 << TCG_REG_R12)
1950
        );
1951

    
1952
    tcg_regset_clear(s->reserved_regs);
1953
    tcg_regset_set_reg(s->reserved_regs, TCG_REG_R0);
1954
    tcg_regset_set_reg(s->reserved_regs, TCG_REG_R1);
1955
#ifndef _CALL_DARWIN
1956
    tcg_regset_set_reg(s->reserved_regs, TCG_REG_R2);
1957
#endif
1958
#ifdef _CALL_SYSV
1959
    tcg_regset_set_reg(s->reserved_regs, TCG_REG_R13);
1960
#endif
1961

    
1962
    tcg_add_target_add_op_defs(ppc_op_defs);
1963
}