Statistics
| Branch: | Revision:

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

History | View | Annotate | Download (58.6 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
#if defined _CALL_DARWIN || defined __APPLE__
28
#define TCG_TARGET_CALL_DARWIN
29
#endif
30

    
31
#ifdef TCG_TARGET_CALL_DARWIN
32
#define LINKAGE_AREA_SIZE 24
33
#define LR_OFFSET 8
34
#elif defined _CALL_AIX
35
#define LINKAGE_AREA_SIZE 52
36
#define LR_OFFSET 8
37
#else
38
#define LINKAGE_AREA_SIZE 8
39
#define LR_OFFSET 4
40
#endif
41

    
42
#ifndef GUEST_BASE
43
#define GUEST_BASE 0
44
#endif
45

    
46
#ifdef CONFIG_USE_GUEST_BASE
47
#define TCG_GUEST_BASE_REG 30
48
#else
49
#define TCG_GUEST_BASE_REG 0
50
#endif
51

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

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

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

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

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

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

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

    
180
    return disp & 0x3fffffc;
181
}
182

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

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

    
193
    disp = target - (tcg_target_long) pc;
194
    if (disp != (int16_t) disp)
195
        tcg_abort ();
196

    
197
    return disp & 0xfffc;
198
}
199

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

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

    
222
/* parse target specific constraints */
223
static int target_parse_constraint(TCGArgConstraint *ct, const char **pct_str)
224
{
225
    const char *ct_str;
226

    
227
    ct_str = *pct_str;
228
    switch (ct_str[0]) {
229
    case 'A': case 'B': case 'C': case 'D':
230
        ct->ct |= TCG_CT_REG;
231
        tcg_regset_set_reg(ct->u.regs, 3 + ct_str[0] - 'A');
232
        break;
233
    case 'r':
234
        ct->ct |= TCG_CT_REG;
235
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
236
        break;
237
#ifdef CONFIG_SOFTMMU
238
    case 'L':                   /* qemu_ld constraint */
239
        ct->ct |= TCG_CT_REG;
240
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
241
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R3);
242
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R4);
243
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R5);
244
#if TARGET_LONG_BITS == 64
245
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R6);
246
#ifdef TCG_TARGET_CALL_ALIGN_ARGS
247
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R7);
248
#endif
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
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R6);
258
#if TARGET_LONG_BITS == 64
259
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R7);
260
#ifdef TCG_TARGET_CALL_ALIGN_ARGS
261
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R8);
262
#endif
263
#endif
264
        break;
265
    case 'M':                   /* qemu_st64 constraint */
266
        ct->ct |= TCG_CT_REG;
267
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
268
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R3);
269
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R4);
270
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R5);
271
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R6);
272
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R7);
273
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R8);
274
#ifdef TCG_TARGET_CALL_ALIGN_ARGS
275
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R9);
276
#endif
277
        break;
278
#else
279
    case 'L':
280
    case 'K':
281
        ct->ct |= TCG_CT_REG;
282
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
283
        break;
284
    case 'M':
285
        ct->ct |= TCG_CT_REG;
286
        tcg_regset_set32(ct->u.regs, 0, 0xffffffff);
287
        tcg_regset_reset_reg(ct->u.regs, TCG_REG_R3);
288
        break;
289
#endif
290
    default:
291
        return -1;
292
    }
293
    ct_str++;
294
    *pct_str = ct_str;
295
    return 0;
296
}
297

    
298
/* test if a constant matches the constraint */
299
static int tcg_target_const_match(tcg_target_long val,
300
                                  const TCGArgConstraint *arg_ct)
301
{
302
    int ct;
303

    
304
    ct = arg_ct->ct;
305
    if (ct & TCG_CT_CONST)
306
        return 1;
307
    return 0;
308
}
309

    
310
#define OPCD(opc) ((opc)<<26)
311
#define XO31(opc) (OPCD(31)|((opc)<<1))
312
#define XO19(opc) (OPCD(19)|((opc)<<1))
313

    
314
#define B      OPCD(18)
315
#define BC     OPCD(16)
316
#define LBZ    OPCD(34)
317
#define LHZ    OPCD(40)
318
#define LHA    OPCD(42)
319
#define LWZ    OPCD(32)
320
#define STB    OPCD(38)
321
#define STH    OPCD(44)
322
#define STW    OPCD(36)
323

    
324
#define ADDIC  OPCD(12)
325
#define ADDI   OPCD(14)
326
#define ADDIS  OPCD(15)
327
#define ORI    OPCD(24)
328
#define ORIS   OPCD(25)
329
#define XORI   OPCD(26)
330
#define XORIS  OPCD(27)
331
#define ANDI   OPCD(28)
332
#define ANDIS  OPCD(29)
333
#define MULLI  OPCD( 7)
334
#define CMPLI  OPCD(10)
335
#define CMPI   OPCD(11)
336
#define SUBFIC OPCD( 8)
337

    
338
#define LWZU   OPCD(33)
339
#define STWU   OPCD(37)
340

    
341
#define RLWIMI OPCD(20)
342
#define RLWINM OPCD(21)
343
#define RLWNM  OPCD(23)
344

    
345
#define BCLR   XO19( 16)
346
#define BCCTR  XO19(528)
347
#define CRAND  XO19(257)
348
#define CRANDC XO19(129)
349
#define CRNAND XO19(225)
350
#define CROR   XO19(449)
351
#define CRNOR  XO19( 33)
352

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

    
387
#define LBZX   XO31( 87)
388
#define LHZX   XO31(279)
389
#define LHAX   XO31(343)
390
#define LWZX   XO31( 23)
391
#define STBX   XO31(215)
392
#define STHX   XO31(407)
393
#define STWX   XO31(151)
394

    
395
#define SPR(a,b) ((((a)<<5)|(b))<<11)
396
#define LR     SPR(8, 0)
397
#define CTR    SPR(9, 0)
398

    
399
#define SLW    XO31( 24)
400
#define SRW    XO31(536)
401
#define SRAW   XO31(792)
402

    
403
#define TW     XO31(4)
404
#define TRAP   (TW | TO (31))
405

    
406
#define RT(r) ((r)<<21)
407
#define RS(r) ((r)<<21)
408
#define RA(r) ((r)<<16)
409
#define RB(r) ((r)<<11)
410
#define TO(t) ((t)<<21)
411
#define SH(s) ((s)<<11)
412
#define MB(b) ((b)<<6)
413
#define ME(e) ((e)<<1)
414
#define BO(o) ((o)<<21)
415

    
416
#define LK    1
417

    
418
#define TAB(t,a,b) (RT(t) | RA(a) | RB(b))
419
#define SAB(s,a,b) (RS(s) | RA(a) | RB(b))
420

    
421
#define BF(n)    ((n)<<23)
422
#define BI(n, c) (((c)+((n)*4))<<16)
423
#define BT(n, c) (((c)+((n)*4))<<21)
424
#define BA(n, c) (((c)+((n)*4))<<16)
425
#define BB(n, c) (((c)+((n)*4))<<11)
426

    
427
#define BO_COND_TRUE  BO (12)
428
#define BO_COND_FALSE BO (4)
429
#define BO_ALWAYS     BO (20)
430

    
431
enum {
432
    CR_LT,
433
    CR_GT,
434
    CR_EQ,
435
    CR_SO
436
};
437

    
438
static const uint32_t tcg_to_bc[] = {
439
    [TCG_COND_EQ]  = BC | BI (7, CR_EQ) | BO_COND_TRUE,
440
    [TCG_COND_NE]  = BC | BI (7, CR_EQ) | BO_COND_FALSE,
441
    [TCG_COND_LT]  = BC | BI (7, CR_LT) | BO_COND_TRUE,
442
    [TCG_COND_GE]  = BC | BI (7, CR_LT) | BO_COND_FALSE,
443
    [TCG_COND_LE]  = BC | BI (7, CR_GT) | BO_COND_FALSE,
444
    [TCG_COND_GT]  = BC | BI (7, CR_GT) | BO_COND_TRUE,
445
    [TCG_COND_LTU] = BC | BI (7, CR_LT) | BO_COND_TRUE,
446
    [TCG_COND_GEU] = BC | BI (7, CR_LT) | BO_COND_FALSE,
447
    [TCG_COND_LEU] = BC | BI (7, CR_GT) | BO_COND_FALSE,
448
    [TCG_COND_GTU] = BC | BI (7, CR_GT) | BO_COND_TRUE,
449
};
450

    
451
static void tcg_out_mov(TCGContext *s, TCGType type, TCGReg ret, TCGReg arg)
452
{
453
    tcg_out32 (s, OR | SAB (arg, ret, arg));
454
}
455

    
456
static void tcg_out_movi(TCGContext *s, TCGType type,
457
                         TCGReg ret, tcg_target_long arg)
458
{
459
    if (arg == (int16_t) arg)
460
        tcg_out32 (s, ADDI | RT (ret) | RA (0) | (arg & 0xffff));
461
    else {
462
        tcg_out32 (s, ADDIS | RT (ret) | RA (0) | ((arg >> 16) & 0xffff));
463
        if (arg & 0xffff)
464
            tcg_out32 (s, ORI | RS (ret) | RA (ret) | (arg & 0xffff));
465
    }
466
}
467

    
468
static void tcg_out_ldst (TCGContext *s, int ret, int addr,
469
                          int offset, int op1, int op2)
470
{
471
    if (offset == (int16_t) offset)
472
        tcg_out32 (s, op1 | RT (ret) | RA (addr) | (offset & 0xffff));
473
    else {
474
        tcg_out_movi (s, TCG_TYPE_I32, 0, offset);
475
        tcg_out32 (s, op2 | RT (ret) | RA (addr) | RB (0));
476
    }
477
}
478

    
479
static void tcg_out_b (TCGContext *s, int mask, tcg_target_long target)
480
{
481
    tcg_target_long disp;
482

    
483
    disp = target - (tcg_target_long) s->code_ptr;
484
    if ((disp << 6) >> 6 == disp)
485
        tcg_out32 (s, B | (disp & 0x3fffffc) | mask);
486
    else {
487
        tcg_out_movi (s, TCG_TYPE_I32, 0, (tcg_target_long) target);
488
        tcg_out32 (s, MTSPR | RS (0) | CTR);
489
        tcg_out32 (s, BCCTR | BO_ALWAYS | mask);
490
    }
491
}
492

    
493
static void tcg_out_call (TCGContext *s, tcg_target_long arg, int const_arg)
494
{
495
#ifdef _CALL_AIX
496
    int reg;
497

    
498
    if (const_arg) {
499
        reg = 2;
500
        tcg_out_movi (s, TCG_TYPE_I32, reg, arg);
501
    }
502
    else reg = arg;
503

    
504
    tcg_out32 (s, LWZ | RT (0) | RA (reg));
505
    tcg_out32 (s, MTSPR | RA (0) | CTR);
506
    tcg_out32 (s, LWZ | RT (2) | RA (reg) | 4);
507
    tcg_out32 (s, BCCTR | BO_ALWAYS | LK);
508
#else
509
    if (const_arg) {
510
        tcg_out_b (s, LK, arg);
511
    }
512
    else {
513
        tcg_out32 (s, MTSPR | RS (arg) | LR);
514
        tcg_out32 (s, BCLR | BO_ALWAYS | LK);
515
    }
516
#endif
517
}
518

    
519
#if defined(CONFIG_SOFTMMU)
520

    
521
static void add_qemu_ldst_label (TCGContext *s,
522
                                 int is_ld,
523
                                 int opc,
524
                                 int data_reg,
525
                                 int data_reg2,
526
                                 int addrlo_reg,
527
                                 int addrhi_reg,
528
                                 int mem_index,
529
                                 uint8_t *raddr,
530
                                 uint8_t *label_ptr)
531
{
532
    int idx;
533
    TCGLabelQemuLdst *label;
534

    
535
    if (s->nb_qemu_ldst_labels >= TCG_MAX_QEMU_LDST) {
536
        tcg_abort();
537
    }
538

    
539
    idx = s->nb_qemu_ldst_labels++;
540
    label = (TCGLabelQemuLdst *)&s->qemu_ldst_labels[idx];
541
    label->is_ld = is_ld;
542
    label->opc = opc;
543
    label->datalo_reg = data_reg;
544
    label->datahi_reg = data_reg2;
545
    label->addrlo_reg = addrlo_reg;
546
    label->addrhi_reg = addrhi_reg;
547
    label->mem_index = mem_index;
548
    label->raddr = raddr;
549
    label->label_ptr[0] = label_ptr;
550
}
551

    
552
#include "../../softmmu_defs.h"
553

    
554
/* helper signature: helper_ld_mmu(CPUState *env, target_ulong addr,
555
   int mmu_idx) */
556
static const void * const qemu_ld_helpers[4] = {
557
    helper_ldb_mmu,
558
    helper_ldw_mmu,
559
    helper_ldl_mmu,
560
    helper_ldq_mmu,
561
};
562

    
563
/* helper signature: helper_st_mmu(CPUState *env, target_ulong addr,
564
   uintxx_t val, int mmu_idx) */
565
static const void * const qemu_st_helpers[4] = {
566
    helper_stb_mmu,
567
    helper_stw_mmu,
568
    helper_stl_mmu,
569
    helper_stq_mmu,
570
};
571

    
572
static void *ld_trampolines[4];
573
static void *st_trampolines[4];
574

    
575
static void tcg_out_tlb_check (TCGContext *s, int r0, int r1, int r2,
576
                               int addr_reg, int addr_reg2, int s_bits,
577
                               int offset1, int offset2, uint8_t **label_ptr)
578
{
579
    uint16_t retranst;
580

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

    
605
    tcg_out32 (s, CMP | BF (7) | RA (r2) | RB (r1));
606
#if TARGET_LONG_BITS == 64
607
    tcg_out32 (s, LWZ | RT (r1) | RA (r0) | 4);
608
    tcg_out32 (s, CMP | BF (6) | RA (addr_reg2) | RB (r1));
609
    tcg_out32 (s, CRAND | BT (7, CR_EQ) | BA (6, CR_EQ) | BB (7, CR_EQ));
610
#endif
611
    *label_ptr = s->code_ptr;
612
    retranst = ((uint16_t *) s->code_ptr)[1] & ~3;
613
    tcg_out32 (s, BC | BI (7, CR_EQ) | retranst | BO_COND_FALSE);
614

    
615
    /* r0 now contains &env->tlb_table[mem_index][index].addr_x */
616
    tcg_out32 (s, (LWZ
617
                   | RT (r0)
618
                   | RA (r0)
619
                   | offset2
620
                   )
621
        );
622
    /* r0 = env->tlb_table[mem_index][index].addend */
623
    tcg_out32 (s, ADD | RT (r0) | RA (r0) | RB (addr_reg));
624
    /* r0 = env->tlb_table[mem_index][index].addend + addr */
625

    
626
}
627
#endif
628

    
629
static void tcg_out_qemu_ld (TCGContext *s, const TCGArg *args, int opc)
630
{
631
    int addr_reg, addr_reg2, data_reg, data_reg2, r0, r1, rbase, bswap;
632
#ifdef CONFIG_SOFTMMU
633
    int mem_index, s_bits, r2;
634
    uint8_t *label_ptr;
635
#endif
636

    
637
    data_reg = *args++;
638
    if (opc == 3)
639
        data_reg2 = *args++;
640
    else
641
        data_reg2 = 0;
642
    addr_reg = *args++;
643

    
644
#ifdef CONFIG_SOFTMMU
645
#if TARGET_LONG_BITS == 64
646
    addr_reg2 = *args++;
647
#else
648
    addr_reg2 = 0;
649
#endif
650
    mem_index = *args;
651
    s_bits = opc & 3;
652
    r0 = 3;
653
    r1 = 4;
654
    r2 = 0;
655
    rbase = 0;
656

    
657
    tcg_out_tlb_check (
658
        s, r0, r1, r2, addr_reg, addr_reg2, s_bits,
659
        offsetof (CPUArchState, tlb_table[mem_index][0].addr_read),
660
        offsetof (CPUTLBEntry, addend) - offsetof (CPUTLBEntry, addr_read),
661
        &label_ptr
662
        );
663
#else  /* !CONFIG_SOFTMMU */
664
    r0 = addr_reg;
665
    r1 = 3;
666
    rbase = GUEST_BASE ? TCG_GUEST_BASE_REG : 0;
667
#endif
668

    
669
#ifdef TARGET_WORDS_BIGENDIAN
670
    bswap = 0;
671
#else
672
    bswap = 1;
673
#endif
674

    
675
    switch (opc) {
676
    default:
677
    case 0:
678
        tcg_out32 (s, LBZX | TAB (data_reg, rbase, r0));
679
        break;
680
    case 0|4:
681
        tcg_out32 (s, LBZX | TAB (data_reg, rbase, r0));
682
        tcg_out32 (s, EXTSB | RA (data_reg) | RS (data_reg));
683
        break;
684
    case 1:
685
        if (bswap)
686
            tcg_out32 (s, LHBRX | TAB (data_reg, rbase, r0));
687
        else
688
            tcg_out32 (s, LHZX | TAB (data_reg, rbase, r0));
689
        break;
690
    case 1|4:
691
        if (bswap) {
692
            tcg_out32 (s, LHBRX | TAB (data_reg, rbase, r0));
693
            tcg_out32 (s, EXTSH | RA (data_reg) | RS (data_reg));
694
        }
695
        else tcg_out32 (s, LHAX | TAB (data_reg, rbase, r0));
696
        break;
697
    case 2:
698
        if (bswap)
699
            tcg_out32 (s, LWBRX | TAB (data_reg, rbase, r0));
700
        else
701
            tcg_out32 (s, LWZX | TAB (data_reg, rbase, r0));
702
        break;
703
    case 3:
704
        if (bswap) {
705
            tcg_out32 (s, ADDI | RT (r1) | RA (r0) | 4);
706
            tcg_out32 (s, LWBRX | TAB (data_reg, rbase, r0));
707
            tcg_out32 (s, LWBRX | TAB (data_reg2, rbase, r1));
708
        }
709
        else {
710
#ifdef CONFIG_USE_GUEST_BASE
711
            tcg_out32 (s, ADDI | RT (r1) | RA (r0) | 4);
712
            tcg_out32 (s, LWZX | TAB (data_reg2, rbase, r0));
713
            tcg_out32 (s, LWZX | TAB (data_reg, rbase, r1));
714
#else
715
            if (r0 == data_reg2) {
716
                tcg_out32 (s, LWZ | RT (0) | RA (r0));
717
                tcg_out32 (s, LWZ | RT (data_reg) | RA (r0) | 4);
718
                tcg_out_mov (s, TCG_TYPE_I32, data_reg2, 0);
719
            }
720
            else {
721
                tcg_out32 (s, LWZ | RT (data_reg2) | RA (r0));
722
                tcg_out32 (s, LWZ | RT (data_reg) | RA (r0) | 4);
723
            }
724
#endif
725
        }
726
        break;
727
    }
728
#ifdef CONFIG_SOFTMMU
729
    add_qemu_ldst_label (s,
730
                         1,
731
                         opc,
732
                         data_reg,
733
                         data_reg2,
734
                         addr_reg,
735
                         addr_reg2,
736
                         mem_index,
737
                         s->code_ptr,
738
                         label_ptr);
739
#endif
740
}
741

    
742
static void tcg_out_qemu_st (TCGContext *s, const TCGArg *args, int opc)
743
{
744
    int addr_reg, addr_reg2, r0, r1, data_reg, data_reg2, bswap, rbase;
745
#ifdef CONFIG_SOFTMMU
746
    int mem_index, r2;
747
    uint8_t *label_ptr;
748
#endif
749

    
750
    data_reg = *args++;
751
    if (opc == 3)
752
        data_reg2 = *args++;
753
    else
754
        data_reg2 = 0;
755
    addr_reg = *args++;
756

    
757
#ifdef CONFIG_SOFTMMU
758
#if TARGET_LONG_BITS == 64
759
    addr_reg2 = *args++;
760
#else
761
    addr_reg2 = 0;
762
#endif
763
    mem_index = *args;
764
    r0 = 3;
765
    r1 = 4;
766
    r2 = 0;
767
    rbase = 0;
768

    
769
    tcg_out_tlb_check (
770
        s, r0, r1, r2, addr_reg, addr_reg2, opc & 3,
771
        offsetof (CPUArchState, tlb_table[mem_index][0].addr_write),
772
        offsetof (CPUTLBEntry, addend) - offsetof (CPUTLBEntry, addr_write),
773
        &label_ptr
774
        );
775
#else  /* !CONFIG_SOFTMMU */
776
    r0 = addr_reg;
777
    r1 = 3;
778
    rbase = GUEST_BASE ? TCG_GUEST_BASE_REG : 0;
779
#endif
780

    
781
#ifdef TARGET_WORDS_BIGENDIAN
782
    bswap = 0;
783
#else
784
    bswap = 1;
785
#endif
786
    switch (opc) {
787
    case 0:
788
        tcg_out32 (s, STBX | SAB (data_reg, rbase, r0));
789
        break;
790
    case 1:
791
        if (bswap)
792
            tcg_out32 (s, STHBRX | SAB (data_reg, rbase, r0));
793
        else
794
            tcg_out32 (s, STHX | SAB (data_reg, rbase, r0));
795
        break;
796
    case 2:
797
        if (bswap)
798
            tcg_out32 (s, STWBRX | SAB (data_reg, rbase, r0));
799
        else
800
            tcg_out32 (s, STWX | SAB (data_reg, rbase, r0));
801
        break;
802
    case 3:
803
        if (bswap) {
804
            tcg_out32 (s, ADDI | RT (r1) | RA (r0) | 4);
805
            tcg_out32 (s, STWBRX | SAB (data_reg,  rbase, r0));
806
            tcg_out32 (s, STWBRX | SAB (data_reg2, rbase, r1));
807
        }
808
        else {
809
#ifdef CONFIG_USE_GUEST_BASE
810
            tcg_out32 (s, STWX | SAB (data_reg2, rbase, r0));
811
            tcg_out32 (s, ADDI | RT (r1) | RA (r0) | 4);
812
            tcg_out32 (s, STWX | SAB (data_reg,  rbase, r1));
813
#else
814
            tcg_out32 (s, STW | RS (data_reg2) | RA (r0));
815
            tcg_out32 (s, STW | RS (data_reg) | RA (r0) | 4);
816
#endif
817
        }
818
        break;
819
    }
820

    
821
#ifdef CONFIG_SOFTMMU
822
    add_qemu_ldst_label (s,
823
                         0,
824
                         opc,
825
                         data_reg,
826
                         data_reg2,
827
                         addr_reg,
828
                         addr_reg2,
829
                         mem_index,
830
                         s->code_ptr,
831
                         label_ptr);
832
#endif
833
}
834

    
835
#if defined(CONFIG_SOFTMMU)
836
static void tcg_out_qemu_ld_slow_path (TCGContext *s, TCGLabelQemuLdst *label)
837
{
838
    int s_bits;
839
    int ir;
840
    int opc = label->opc;
841
    int mem_index = label->mem_index;
842
    int data_reg = label->datalo_reg;
843
    int data_reg2 = label->datahi_reg;
844
    int addr_reg = label->addrlo_reg;
845
    uint8_t *raddr = label->raddr;
846
    uint8_t **label_ptr = &label->label_ptr[0];
847

    
848
    s_bits = opc & 3;
849

    
850
    /* resolve label address */
851
    reloc_pc14 (label_ptr[0], (tcg_target_long) s->code_ptr);
852

    
853
    /* slow path */
854
    ir = 4;
855
#if TARGET_LONG_BITS == 32
856
    tcg_out_mov (s, TCG_TYPE_I32, ir++, addr_reg);
857
#else
858
#ifdef TCG_TARGET_CALL_ALIGN_ARGS
859
    ir |= 1;
860
#endif
861
    tcg_out_mov (s, TCG_TYPE_I32, ir++, label->addrhi_reg);
862
    tcg_out_mov (s, TCG_TYPE_I32, ir++, addr_reg);
863
#endif
864
    tcg_out_movi (s, TCG_TYPE_I32, ir, mem_index);
865
    tcg_out_call (s, (tcg_target_long) ld_trampolines[s_bits], 1);
866
    tcg_out32 (s, (tcg_target_long) raddr);
867
    switch (opc) {
868
    case 0|4:
869
        tcg_out32 (s, EXTSB | RA (data_reg) | RS (3));
870
        break;
871
    case 1|4:
872
        tcg_out32 (s, EXTSH | RA (data_reg) | RS (3));
873
        break;
874
    case 0:
875
    case 1:
876
    case 2:
877
        if (data_reg != 3)
878
            tcg_out_mov (s, TCG_TYPE_I32, data_reg, 3);
879
        break;
880
    case 3:
881
        if (data_reg == 3) {
882
            if (data_reg2 == 4) {
883
                tcg_out_mov (s, TCG_TYPE_I32, 0, 4);
884
                tcg_out_mov (s, TCG_TYPE_I32, 4, 3);
885
                tcg_out_mov (s, TCG_TYPE_I32, 3, 0);
886
            }
887
            else {
888
                tcg_out_mov (s, TCG_TYPE_I32, data_reg2, 3);
889
                tcg_out_mov (s, TCG_TYPE_I32, 3, 4);
890
            }
891
        }
892
        else {
893
            if (data_reg != 4) tcg_out_mov (s, TCG_TYPE_I32, data_reg, 4);
894
            if (data_reg2 != 3) tcg_out_mov (s, TCG_TYPE_I32, data_reg2, 3);
895
        }
896
        break;
897
    }
898
    /* Jump to the code corresponding to next IR of qemu_st */
899
    tcg_out_b (s, 0, (tcg_target_long) raddr);
900
}
901

    
902
static void tcg_out_qemu_st_slow_path (TCGContext *s, TCGLabelQemuLdst *label)
903
{
904
    int ir;
905
    int opc = label->opc;
906
    int mem_index = label->mem_index;
907
    int data_reg = label->datalo_reg;
908
    int data_reg2 = label->datahi_reg;
909
    int addr_reg = label->addrlo_reg;
910
    uint8_t *raddr = label->raddr;
911
    uint8_t **label_ptr = &label->label_ptr[0];
912

    
913
    /* resolve label address */
914
    reloc_pc14 (label_ptr[0], (tcg_target_long) s->code_ptr);
915

    
916
    /* slow path */
917
    ir = 4;
918
#if TARGET_LONG_BITS == 32
919
    tcg_out_mov (s, TCG_TYPE_I32, ir++, addr_reg);
920
#else
921
#ifdef TCG_TARGET_CALL_ALIGN_ARGS
922
    ir |= 1;
923
#endif
924
    tcg_out_mov (s, TCG_TYPE_I32, ir++, label->addrhi_reg);
925
    tcg_out_mov (s, TCG_TYPE_I32, ir++, addr_reg);
926
#endif
927

    
928
    switch (opc) {
929
    case 0:
930
        tcg_out32 (s, (RLWINM
931
                       | RA (ir)
932
                       | RS (data_reg)
933
                       | SH (0)
934
                       | MB (24)
935
                       | ME (31)));
936
        break;
937
    case 1:
938
        tcg_out32 (s, (RLWINM
939
                       | RA (ir)
940
                       | RS (data_reg)
941
                       | SH (0)
942
                       | MB (16)
943
                       | ME (31)));
944
        break;
945
    case 2:
946
        tcg_out_mov (s, TCG_TYPE_I32, ir, data_reg);
947
        break;
948
    case 3:
949
#ifdef TCG_TARGET_CALL_ALIGN_ARGS
950
        ir |= 1;
951
#endif
952
        tcg_out_mov (s, TCG_TYPE_I32, ir++, data_reg2);
953
        tcg_out_mov (s, TCG_TYPE_I32, ir, data_reg);
954
        break;
955
    }
956
    ir++;
957

    
958
    tcg_out_movi (s, TCG_TYPE_I32, ir, mem_index);
959
    tcg_out_call (s, (tcg_target_long) st_trampolines[opc], 1);
960
    tcg_out32 (s, (tcg_target_long) raddr);
961
    tcg_out_b (s, 0, (tcg_target_long) raddr);
962
}
963

    
964
void tcg_out_tb_finalize(TCGContext *s)
965
{
966
    int i;
967
    TCGLabelQemuLdst *label;
968

    
969
    /* qemu_ld/st slow paths */
970
    for (i = 0; i < s->nb_qemu_ldst_labels; i++) {
971
        label = (TCGLabelQemuLdst *) &s->qemu_ldst_labels[i];
972
        if (label->is_ld) {
973
            tcg_out_qemu_ld_slow_path (s, label);
974
        }
975
        else {
976
            tcg_out_qemu_st_slow_path (s, label);
977
        }
978
    }
979
}
980
#endif
981

    
982
static void emit_ldst_trampoline (TCGContext *s, const void *ptr)
983
{
984
    tcg_out32 (s, MFSPR | RT (3) | LR);
985
    tcg_out32 (s, ADDI | RT (3) | RA (3) | 4);
986
    tcg_out32 (s, MTSPR | RS (3) | LR);
987
    tcg_out_mov (s, TCG_TYPE_I32, 3, TCG_AREG0);
988
    tcg_out_b (s, 0, (tcg_target_long) ptr);
989
}
990

    
991
static void tcg_target_qemu_prologue (TCGContext *s)
992
{
993
    int i, frame_size;
994

    
995
    frame_size = 0
996
        + LINKAGE_AREA_SIZE
997
        + TCG_STATIC_CALL_ARGS_SIZE
998
        + ARRAY_SIZE (tcg_target_callee_save_regs) * 4
999
        + CPU_TEMP_BUF_NLONGS * sizeof(long)
1000
        ;
1001
    frame_size = (frame_size + 15) & ~15;
1002

    
1003
    tcg_set_frame(s, TCG_REG_CALL_STACK, frame_size
1004
                  - CPU_TEMP_BUF_NLONGS * sizeof(long),
1005
                  CPU_TEMP_BUF_NLONGS * sizeof(long));
1006

    
1007
#ifdef _CALL_AIX
1008
    {
1009
        uint32_t addr;
1010

    
1011
        /* First emit adhoc function descriptor */
1012
        addr = (uint32_t) s->code_ptr + 12;
1013
        tcg_out32 (s, addr);        /* entry point */
1014
        s->code_ptr += 8;           /* skip TOC and environment pointer */
1015
    }
1016
#endif
1017
    tcg_out32 (s, MFSPR | RT (0) | LR);
1018
    tcg_out32 (s, STWU | RS (1) | RA (1) | (-frame_size & 0xffff));
1019
    for (i = 0; i < ARRAY_SIZE (tcg_target_callee_save_regs); ++i)
1020
        tcg_out32 (s, (STW
1021
                       | RS (tcg_target_callee_save_regs[i])
1022
                       | RA (1)
1023
                       | (i * 4 + LINKAGE_AREA_SIZE + TCG_STATIC_CALL_ARGS_SIZE)
1024
                       )
1025
            );
1026
    tcg_out32 (s, STW | RS (0) | RA (1) | (frame_size + LR_OFFSET));
1027

    
1028
#ifdef CONFIG_USE_GUEST_BASE
1029
    if (GUEST_BASE) {
1030
        tcg_out_movi (s, TCG_TYPE_I32, TCG_GUEST_BASE_REG, GUEST_BASE);
1031
        tcg_regset_set_reg(s->reserved_regs, TCG_GUEST_BASE_REG);
1032
    }
1033
#endif
1034

    
1035
    tcg_out_mov (s, TCG_TYPE_PTR, TCG_AREG0, tcg_target_call_iarg_regs[0]);
1036
    tcg_out32 (s, MTSPR | RS (tcg_target_call_iarg_regs[1]) | CTR);
1037
    tcg_out32 (s, BCCTR | BO_ALWAYS);
1038
    tb_ret_addr = s->code_ptr;
1039

    
1040
    for (i = 0; i < ARRAY_SIZE (tcg_target_callee_save_regs); ++i)
1041
        tcg_out32 (s, (LWZ
1042
                       | RT (tcg_target_callee_save_regs[i])
1043
                       | RA (1)
1044
                       | (i * 4 + LINKAGE_AREA_SIZE + TCG_STATIC_CALL_ARGS_SIZE)
1045
                       )
1046
            );
1047
    tcg_out32 (s, LWZ | RT (0) | RA (1) | (frame_size + LR_OFFSET));
1048
    tcg_out32 (s, MTSPR | RS (0) | LR);
1049
    tcg_out32 (s, ADDI | RT (1) | RA (1) | frame_size);
1050
    tcg_out32 (s, BCLR | BO_ALWAYS);
1051

    
1052
    for (i = 0; i < 4; ++i) {
1053
        ld_trampolines[i] = s->code_ptr;
1054
        emit_ldst_trampoline (s, qemu_ld_helpers[i]);
1055

    
1056
        st_trampolines[i] = s->code_ptr;
1057
        emit_ldst_trampoline (s, qemu_st_helpers[i]);
1058
    }
1059
}
1060

    
1061
static void tcg_out_ld (TCGContext *s, TCGType type, TCGReg ret, TCGReg arg1,
1062
                        tcg_target_long arg2)
1063
{
1064
    tcg_out_ldst (s, ret, arg1, arg2, LWZ, LWZX);
1065
}
1066

    
1067
static void tcg_out_st (TCGContext *s, TCGType type, TCGReg arg, TCGReg arg1,
1068
                        tcg_target_long arg2)
1069
{
1070
    tcg_out_ldst (s, arg, arg1, arg2, STW, STWX);
1071
}
1072

    
1073
static void ppc_addi (TCGContext *s, int rt, int ra, tcg_target_long si)
1074
{
1075
    if (!si && rt == ra)
1076
        return;
1077

    
1078
    if (si == (int16_t) si)
1079
        tcg_out32 (s, ADDI | RT (rt) | RA (ra) | (si & 0xffff));
1080
    else {
1081
        uint16_t h = ((si >> 16) & 0xffff) + ((uint16_t) si >> 15);
1082
        tcg_out32 (s, ADDIS | RT (rt) | RA (ra) | h);
1083
        tcg_out32 (s, ADDI | RT (rt) | RA (rt) | (si & 0xffff));
1084
    }
1085
}
1086

    
1087
static void tcg_out_cmp (TCGContext *s, int cond, TCGArg arg1, TCGArg arg2,
1088
                         int const_arg2, int cr)
1089
{
1090
    int imm;
1091
    uint32_t op;
1092

    
1093
    switch (cond) {
1094
    case TCG_COND_EQ:
1095
    case TCG_COND_NE:
1096
        if (const_arg2) {
1097
            if ((int16_t) arg2 == arg2) {
1098
                op = CMPI;
1099
                imm = 1;
1100
                break;
1101
            }
1102
            else if ((uint16_t) arg2 == arg2) {
1103
                op = CMPLI;
1104
                imm = 1;
1105
                break;
1106
            }
1107
        }
1108
        op = CMPL;
1109
        imm = 0;
1110
        break;
1111

    
1112
    case TCG_COND_LT:
1113
    case TCG_COND_GE:
1114
    case TCG_COND_LE:
1115
    case TCG_COND_GT:
1116
        if (const_arg2) {
1117
            if ((int16_t) arg2 == arg2) {
1118
                op = CMPI;
1119
                imm = 1;
1120
                break;
1121
            }
1122
        }
1123
        op = CMP;
1124
        imm = 0;
1125
        break;
1126

    
1127
    case TCG_COND_LTU:
1128
    case TCG_COND_GEU:
1129
    case TCG_COND_LEU:
1130
    case TCG_COND_GTU:
1131
        if (const_arg2) {
1132
            if ((uint16_t) arg2 == arg2) {
1133
                op = CMPLI;
1134
                imm = 1;
1135
                break;
1136
            }
1137
        }
1138
        op = CMPL;
1139
        imm = 0;
1140
        break;
1141

    
1142
    default:
1143
        tcg_abort ();
1144
    }
1145
    op |= BF (cr);
1146

    
1147
    if (imm)
1148
        tcg_out32 (s, op | RA (arg1) | (arg2 & 0xffff));
1149
    else {
1150
        if (const_arg2) {
1151
            tcg_out_movi (s, TCG_TYPE_I32, 0, arg2);
1152
            tcg_out32 (s, op | RA (arg1) | RB (0));
1153
        }
1154
        else
1155
            tcg_out32 (s, op | RA (arg1) | RB (arg2));
1156
    }
1157

    
1158
}
1159

    
1160
static void tcg_out_bc (TCGContext *s, int bc, int label_index)
1161
{
1162
    TCGLabel *l = &s->labels[label_index];
1163

    
1164
    if (l->has_value)
1165
        tcg_out32 (s, bc | reloc_pc14_val (s->code_ptr, l->u.value));
1166
    else {
1167
        uint16_t val = *(uint16_t *) &s->code_ptr[2];
1168

    
1169
        /* Thanks to Andrzej Zaborowski */
1170
        tcg_out32 (s, bc | (val & 0xfffc));
1171
        tcg_out_reloc (s, s->code_ptr - 4, R_PPC_REL14, label_index, 0);
1172
    }
1173
}
1174

    
1175
static void tcg_out_cr7eq_from_cond (TCGContext *s, const TCGArg *args,
1176
                                     const int *const_args)
1177
{
1178
    TCGCond cond = args[4];
1179
    int op;
1180
    struct { int bit1; int bit2; int cond2; } bits[] = {
1181
        [TCG_COND_LT ] = { CR_LT, CR_LT, TCG_COND_LT  },
1182
        [TCG_COND_LE ] = { CR_LT, CR_GT, TCG_COND_LT  },
1183
        [TCG_COND_GT ] = { CR_GT, CR_GT, TCG_COND_GT  },
1184
        [TCG_COND_GE ] = { CR_GT, CR_LT, TCG_COND_GT  },
1185
        [TCG_COND_LTU] = { CR_LT, CR_LT, TCG_COND_LTU },
1186
        [TCG_COND_LEU] = { CR_LT, CR_GT, TCG_COND_LTU },
1187
        [TCG_COND_GTU] = { CR_GT, CR_GT, TCG_COND_GTU },
1188
        [TCG_COND_GEU] = { CR_GT, CR_LT, TCG_COND_GTU },
1189
    }, *b = &bits[cond];
1190

    
1191
    switch (cond) {
1192
    case TCG_COND_EQ:
1193
    case TCG_COND_NE:
1194
        op = (cond == TCG_COND_EQ) ? CRAND : CRNAND;
1195
        tcg_out_cmp (s, cond, args[0], args[2], const_args[2], 6);
1196
        tcg_out_cmp (s, cond, args[1], args[3], const_args[3], 7);
1197
        tcg_out32 (s, op | BT (7, CR_EQ) | BA (6, CR_EQ) | BB (7, CR_EQ));
1198
        break;
1199
    case TCG_COND_LT:
1200
    case TCG_COND_LE:
1201
    case TCG_COND_GT:
1202
    case TCG_COND_GE:
1203
    case TCG_COND_LTU:
1204
    case TCG_COND_LEU:
1205
    case TCG_COND_GTU:
1206
    case TCG_COND_GEU:
1207
        op = (b->bit1 != b->bit2) ? CRANDC : CRAND;
1208
        tcg_out_cmp (s, b->cond2, args[1], args[3], const_args[3], 5);
1209
        tcg_out_cmp (s, tcg_unsigned_cond (cond), args[0], args[2],
1210
                     const_args[2], 7);
1211
        tcg_out32 (s, op | BT (7, CR_EQ) | BA (5, CR_EQ) | BB (7, b->bit2));
1212
        tcg_out32 (s, CROR | BT (7, CR_EQ) | BA (5, b->bit1) | BB (7, CR_EQ));
1213
        break;
1214
    default:
1215
        tcg_abort();
1216
    }
1217
}
1218

    
1219
static void tcg_out_setcond (TCGContext *s, TCGCond cond, TCGArg arg0,
1220
                             TCGArg arg1, TCGArg arg2, int const_arg2)
1221
{
1222
    int crop, sh, arg;
1223

    
1224
    switch (cond) {
1225
    case TCG_COND_EQ:
1226
        if (const_arg2) {
1227
            if (!arg2) {
1228
                arg = arg1;
1229
            }
1230
            else {
1231
                arg = 0;
1232
                if ((uint16_t) arg2 == arg2) {
1233
                    tcg_out32 (s, XORI | RS (arg1) | RA (0) | arg2);
1234
                }
1235
                else {
1236
                    tcg_out_movi (s, TCG_TYPE_I32, 0, arg2);
1237
                    tcg_out32 (s, XOR | SAB (arg1, 0, 0));
1238
                }
1239
            }
1240
        }
1241
        else {
1242
            arg = 0;
1243
            tcg_out32 (s, XOR | SAB (arg1, 0, arg2));
1244
        }
1245
        tcg_out32 (s, CNTLZW | RS (arg) | RA (0));
1246
        tcg_out32 (s, (RLWINM
1247
                       | RA (arg0)
1248
                       | RS (0)
1249
                       | SH (27)
1250
                       | MB (5)
1251
                       | ME (31)
1252
                       )
1253
            );
1254
        break;
1255

    
1256
    case TCG_COND_NE:
1257
        if (const_arg2) {
1258
            if (!arg2) {
1259
                arg = arg1;
1260
            }
1261
            else {
1262
                arg = 0;
1263
                if ((uint16_t) arg2 == arg2) {
1264
                    tcg_out32 (s, XORI | RS (arg1) | RA (0) | arg2);
1265
                }
1266
                else {
1267
                    tcg_out_movi (s, TCG_TYPE_I32, 0, arg2);
1268
                    tcg_out32 (s, XOR | SAB (arg1, 0, 0));
1269
                }
1270
            }
1271
        }
1272
        else {
1273
            arg = 0;
1274
            tcg_out32 (s, XOR | SAB (arg1, 0, arg2));
1275
        }
1276

    
1277
        if (arg == arg1 && arg1 == arg0) {
1278
            tcg_out32 (s, ADDIC | RT (0) | RA (arg) | 0xffff);
1279
            tcg_out32 (s, SUBFE | TAB (arg0, 0, arg));
1280
        }
1281
        else {
1282
            tcg_out32 (s, ADDIC | RT (arg0) | RA (arg) | 0xffff);
1283
            tcg_out32 (s, SUBFE | TAB (arg0, arg0, arg));
1284
        }
1285
        break;
1286

    
1287
    case TCG_COND_GT:
1288
    case TCG_COND_GTU:
1289
        sh = 30;
1290
        crop = 0;
1291
        goto crtest;
1292

    
1293
    case TCG_COND_LT:
1294
    case TCG_COND_LTU:
1295
        sh = 29;
1296
        crop = 0;
1297
        goto crtest;
1298

    
1299
    case TCG_COND_GE:
1300
    case TCG_COND_GEU:
1301
        sh = 31;
1302
        crop = CRNOR | BT (7, CR_EQ) | BA (7, CR_LT) | BB (7, CR_LT);
1303
        goto crtest;
1304

    
1305
    case TCG_COND_LE:
1306
    case TCG_COND_LEU:
1307
        sh = 31;
1308
        crop = CRNOR | BT (7, CR_EQ) | BA (7, CR_GT) | BB (7, CR_GT);
1309
    crtest:
1310
        tcg_out_cmp (s, cond, arg1, arg2, const_arg2, 7);
1311
        if (crop) tcg_out32 (s, crop);
1312
        tcg_out32 (s, MFCR | RT (0));
1313
        tcg_out32 (s, (RLWINM
1314
                       | RA (arg0)
1315
                       | RS (0)
1316
                       | SH (sh)
1317
                       | MB (31)
1318
                       | ME (31)
1319
                       )
1320
            );
1321
        break;
1322

    
1323
    default:
1324
        tcg_abort ();
1325
    }
1326
}
1327

    
1328
static void tcg_out_setcond2 (TCGContext *s, const TCGArg *args,
1329
                              const int *const_args)
1330
{
1331
    tcg_out_cr7eq_from_cond (s, args + 1, const_args + 1);
1332
    tcg_out32 (s, MFCR | RT (0));
1333
    tcg_out32 (s, (RLWINM
1334
                   | RA (args[0])
1335
                   | RS (0)
1336
                   | SH (31)
1337
                   | MB (31)
1338
                   | ME (31)
1339
                   )
1340
        );
1341
}
1342

    
1343
static void tcg_out_movcond (TCGContext *s, TCGCond cond,
1344
                             TCGArg dest,
1345
                             TCGArg c1, TCGArg c2,
1346
                             TCGArg v1, TCGArg v2,
1347
                             int const_c2)
1348
{
1349
    tcg_out_cmp (s, cond, c1, c2, const_c2, 7);
1350

    
1351
    if (1) {
1352
        /* At least here on 7747A bit twiddling hacks are outperformed
1353
           by jumpy code (the testing was not scientific) */
1354
        if (dest == v2) {
1355
            cond = tcg_invert_cond (cond);
1356
            v2 = v1;
1357
        }
1358
        else {
1359
            if (dest != v1) {
1360
                tcg_out_mov (s, TCG_TYPE_I32, dest, v1);
1361
            }
1362
        }
1363
        /* Branch forward over one insn */
1364
        tcg_out32 (s, tcg_to_bc[cond] | 8);
1365
        tcg_out_mov (s, TCG_TYPE_I32, dest, v2);
1366
    }
1367
    else {
1368
        /* isel version, "if (1)" above should be replaced once a way
1369
           to figure out availability of isel on the underlying
1370
           hardware is found */
1371
        int tab, bc;
1372

    
1373
        switch (cond) {
1374
        case TCG_COND_EQ:
1375
            tab = TAB (dest, v1, v2);
1376
            bc = CR_EQ;
1377
            break;
1378
        case TCG_COND_NE:
1379
            tab = TAB (dest, v2, v1);
1380
            bc = CR_EQ;
1381
            break;
1382
        case TCG_COND_LTU:
1383
        case TCG_COND_LT:
1384
            tab = TAB (dest, v1, v2);
1385
            bc = CR_LT;
1386
            break;
1387
        case TCG_COND_GEU:
1388
        case TCG_COND_GE:
1389
            tab = TAB (dest, v2, v1);
1390
            bc = CR_LT;
1391
            break;
1392
        case TCG_COND_LEU:
1393
        case TCG_COND_LE:
1394
            tab = TAB (dest, v2, v1);
1395
            bc = CR_GT;
1396
            break;
1397
        case TCG_COND_GTU:
1398
        case TCG_COND_GT:
1399
            tab = TAB (dest, v1, v2);
1400
            bc = CR_GT;
1401
            break;
1402
        default:
1403
            tcg_abort ();
1404
        }
1405
        tcg_out32 (s, ISEL | tab | ((bc + 28) << 6));
1406
    }
1407
}
1408

    
1409
static void tcg_out_brcond (TCGContext *s, TCGCond cond,
1410
                            TCGArg arg1, TCGArg arg2, int const_arg2,
1411
                            int label_index)
1412
{
1413
    tcg_out_cmp (s, cond, arg1, arg2, const_arg2, 7);
1414
    tcg_out_bc (s, tcg_to_bc[cond], label_index);
1415
}
1416

    
1417
/* XXX: we implement it at the target level to avoid having to
1418
   handle cross basic blocks temporaries */
1419
static void tcg_out_brcond2 (TCGContext *s, const TCGArg *args,
1420
                             const int *const_args)
1421
{
1422
    tcg_out_cr7eq_from_cond (s, args, const_args);
1423
    tcg_out_bc (s, (BC | BI (7, CR_EQ) | BO_COND_TRUE), args[5]);
1424
}
1425

    
1426
void ppc_tb_set_jmp_target (unsigned long jmp_addr, unsigned long addr)
1427
{
1428
    uint32_t *ptr;
1429
    long disp = addr - jmp_addr;
1430
    unsigned long patch_size;
1431

    
1432
    ptr = (uint32_t *)jmp_addr;
1433

    
1434
    if ((disp << 6) >> 6 != disp) {
1435
        ptr[0] = 0x3c000000 | (addr >> 16);    /* lis 0,addr@ha */
1436
        ptr[1] = 0x60000000 | (addr & 0xffff); /* la  0,addr@l(0) */
1437
        ptr[2] = 0x7c0903a6;                   /* mtctr 0 */
1438
        ptr[3] = 0x4e800420;                   /* brctr */
1439
        patch_size = 16;
1440
    } else {
1441
        /* patch the branch destination */
1442
        if (disp != 16) {
1443
            *ptr = 0x48000000 | (disp & 0x03fffffc); /* b disp */
1444
            patch_size = 4;
1445
        } else {
1446
            ptr[0] = 0x60000000; /* nop */
1447
            ptr[1] = 0x60000000;
1448
            ptr[2] = 0x60000000;
1449
            ptr[3] = 0x60000000;
1450
            patch_size = 16;
1451
        }
1452
    }
1453
    /* flush icache */
1454
    flush_icache_range(jmp_addr, jmp_addr + patch_size);
1455
}
1456

    
1457
static void tcg_out_op(TCGContext *s, TCGOpcode opc, const TCGArg *args,
1458
                       const int *const_args)
1459
{
1460
    switch (opc) {
1461
    case INDEX_op_exit_tb:
1462
        tcg_out_movi (s, TCG_TYPE_I32, TCG_REG_R3, args[0]);
1463
        tcg_out_b (s, 0, (tcg_target_long) tb_ret_addr);
1464
        break;
1465
    case INDEX_op_goto_tb:
1466
        if (s->tb_jmp_offset) {
1467
            /* direct jump method */
1468

    
1469
            s->tb_jmp_offset[args[0]] = s->code_ptr - s->code_buf;
1470
            s->code_ptr += 16;
1471
        }
1472
        else {
1473
            tcg_abort ();
1474
        }
1475
        s->tb_next_offset[args[0]] = s->code_ptr - s->code_buf;
1476
        break;
1477
    case INDEX_op_br:
1478
        {
1479
            TCGLabel *l = &s->labels[args[0]];
1480

    
1481
            if (l->has_value) {
1482
                tcg_out_b (s, 0, l->u.value);
1483
            }
1484
            else {
1485
                uint32_t val = *(uint32_t *) s->code_ptr;
1486

    
1487
                /* Thanks to Andrzej Zaborowski */
1488
                tcg_out32 (s, B | (val & 0x3fffffc));
1489
                tcg_out_reloc (s, s->code_ptr - 4, R_PPC_REL24, args[0], 0);
1490
            }
1491
        }
1492
        break;
1493
    case INDEX_op_call:
1494
        tcg_out_call (s, args[0], const_args[0]);
1495
        break;
1496
    case INDEX_op_movi_i32:
1497
        tcg_out_movi(s, TCG_TYPE_I32, args[0], args[1]);
1498
        break;
1499
    case INDEX_op_ld8u_i32:
1500
        tcg_out_ldst (s, args[0], args[1], args[2], LBZ, LBZX);
1501
        break;
1502
    case INDEX_op_ld8s_i32:
1503
        tcg_out_ldst (s, args[0], args[1], args[2], LBZ, LBZX);
1504
        tcg_out32 (s, EXTSB | RS (args[0]) | RA (args[0]));
1505
        break;
1506
    case INDEX_op_ld16u_i32:
1507
        tcg_out_ldst (s, args[0], args[1], args[2], LHZ, LHZX);
1508
        break;
1509
    case INDEX_op_ld16s_i32:
1510
        tcg_out_ldst (s, args[0], args[1], args[2], LHA, LHAX);
1511
        break;
1512
    case INDEX_op_ld_i32:
1513
        tcg_out_ldst (s, args[0], args[1], args[2], LWZ, LWZX);
1514
        break;
1515
    case INDEX_op_st8_i32:
1516
        tcg_out_ldst (s, args[0], args[1], args[2], STB, STBX);
1517
        break;
1518
    case INDEX_op_st16_i32:
1519
        tcg_out_ldst (s, args[0], args[1], args[2], STH, STHX);
1520
        break;
1521
    case INDEX_op_st_i32:
1522
        tcg_out_ldst (s, args[0], args[1], args[2], STW, STWX);
1523
        break;
1524

    
1525
    case INDEX_op_add_i32:
1526
        if (const_args[2])
1527
            ppc_addi (s, args[0], args[1], args[2]);
1528
        else
1529
            tcg_out32 (s, ADD | TAB (args[0], args[1], args[2]));
1530
        break;
1531
    case INDEX_op_sub_i32:
1532
        if (const_args[2])
1533
            ppc_addi (s, args[0], args[1], -args[2]);
1534
        else
1535
            tcg_out32 (s, SUBF | TAB (args[0], args[2], args[1]));
1536
        break;
1537

    
1538
    case INDEX_op_and_i32:
1539
        if (const_args[2]) {
1540
            uint32_t c;
1541

    
1542
            c = args[2];
1543

    
1544
            if (!c) {
1545
                tcg_out_movi (s, TCG_TYPE_I32, args[0], 0);
1546
                break;
1547
            }
1548
#ifdef __PPU__
1549
            uint32_t t, n;
1550
            int mb, me;
1551

    
1552
            n = c ^ -(c & 1);
1553
            t = n + (n & -n);
1554

    
1555
            if ((t & (t - 1)) == 0) {
1556
                int lzc, tzc;
1557

    
1558
                if ((c & 0x80000001) == 0x80000001) {
1559
                    lzc = clz32 (n);
1560
                    tzc = ctz32 (n);
1561

    
1562
                    mb = 32 - tzc;
1563
                    me = lzc - 1;
1564
                }
1565
                else {
1566
                    lzc = clz32 (c);
1567
                    tzc = ctz32 (c);
1568

    
1569
                    mb = lzc;
1570
                    me = 31 - tzc;
1571
                }
1572

    
1573
                tcg_out32 (s, (RLWINM
1574
                               | RA (args[0])
1575
                               | RS (args[1])
1576
                               | SH (0)
1577
                               | MB (mb)
1578
                               | ME (me)
1579
                               )
1580
                    );
1581
            }
1582
            else
1583
#endif /* !__PPU__ */
1584
            {
1585
                if ((c & 0xffff) == c)
1586
                    tcg_out32 (s, ANDI | RS (args[1]) | RA (args[0]) | c);
1587
                else if ((c & 0xffff0000) == c)
1588
                    tcg_out32 (s, ANDIS | RS (args[1]) | RA (args[0])
1589
                               | ((c >> 16) & 0xffff));
1590
                else {
1591
                    tcg_out_movi (s, TCG_TYPE_I32, 0, c);
1592
                    tcg_out32 (s, AND | SAB (args[1], args[0], 0));
1593
                }
1594
            }
1595
        }
1596
        else
1597
            tcg_out32 (s, AND | SAB (args[1], args[0], args[2]));
1598
        break;
1599
    case INDEX_op_or_i32:
1600
        if (const_args[2]) {
1601
            if (args[2] & 0xffff) {
1602
                tcg_out32 (s, ORI | RS (args[1])  | RA (args[0])
1603
                           | (args[2] & 0xffff));
1604
                if (args[2] >> 16)
1605
                    tcg_out32 (s, ORIS | RS (args[0])  | RA (args[0])
1606
                               | ((args[2] >> 16) & 0xffff));
1607
            }
1608
            else {
1609
                tcg_out32 (s, ORIS | RS (args[1])  | RA (args[0])
1610
                           | ((args[2] >> 16) & 0xffff));
1611
            }
1612
        }
1613
        else
1614
            tcg_out32 (s, OR | SAB (args[1], args[0], args[2]));
1615
        break;
1616
    case INDEX_op_xor_i32:
1617
        if (const_args[2]) {
1618
            if ((args[2] & 0xffff) == args[2])
1619
                tcg_out32 (s, XORI | RS (args[1])  | RA (args[0])
1620
                           | (args[2] & 0xffff));
1621
            else if ((args[2] & 0xffff0000) == args[2])
1622
                tcg_out32 (s, XORIS | RS (args[1])  | RA (args[0])
1623
                           | ((args[2] >> 16) & 0xffff));
1624
            else {
1625
                tcg_out_movi (s, TCG_TYPE_I32, 0, args[2]);
1626
                tcg_out32 (s, XOR | SAB (args[1], args[0], 0));
1627
            }
1628
        }
1629
        else
1630
            tcg_out32 (s, XOR | SAB (args[1], args[0], args[2]));
1631
        break;
1632
    case INDEX_op_andc_i32:
1633
        tcg_out32 (s, ANDC | SAB (args[1], args[0], args[2]));
1634
        break;
1635
    case INDEX_op_orc_i32:
1636
        tcg_out32 (s, ORC | SAB (args[1], args[0], args[2]));
1637
        break;
1638
    case INDEX_op_eqv_i32:
1639
        tcg_out32 (s, EQV | SAB (args[1], args[0], args[2]));
1640
        break;
1641
    case INDEX_op_nand_i32:
1642
        tcg_out32 (s, NAND | SAB (args[1], args[0], args[2]));
1643
        break;
1644
    case INDEX_op_nor_i32:
1645
        tcg_out32 (s, NOR | SAB (args[1], args[0], args[2]));
1646
        break;
1647

    
1648
    case INDEX_op_mul_i32:
1649
        if (const_args[2]) {
1650
            if (args[2] == (int16_t) args[2])
1651
                tcg_out32 (s, MULLI | RT (args[0]) | RA (args[1])
1652
                           | (args[2] & 0xffff));
1653
            else {
1654
                tcg_out_movi (s, TCG_TYPE_I32, 0, args[2]);
1655
                tcg_out32 (s, MULLW | TAB (args[0], args[1], 0));
1656
            }
1657
        }
1658
        else
1659
            tcg_out32 (s, MULLW | TAB (args[0], args[1], args[2]));
1660
        break;
1661

    
1662
    case INDEX_op_div_i32:
1663
        tcg_out32 (s, DIVW | TAB (args[0], args[1], args[2]));
1664
        break;
1665

    
1666
    case INDEX_op_divu_i32:
1667
        tcg_out32 (s, DIVWU | TAB (args[0], args[1], args[2]));
1668
        break;
1669

    
1670
    case INDEX_op_rem_i32:
1671
        tcg_out32 (s, DIVW | TAB (0, args[1], args[2]));
1672
        tcg_out32 (s, MULLW | TAB (0, 0, args[2]));
1673
        tcg_out32 (s, SUBF | TAB (args[0], 0, args[1]));
1674
        break;
1675

    
1676
    case INDEX_op_remu_i32:
1677
        tcg_out32 (s, DIVWU | TAB (0, args[1], args[2]));
1678
        tcg_out32 (s, MULLW | TAB (0, 0, args[2]));
1679
        tcg_out32 (s, SUBF | TAB (args[0], 0, args[1]));
1680
        break;
1681

    
1682
    case INDEX_op_mulu2_i32:
1683
        if (args[0] == args[2] || args[0] == args[3]) {
1684
            tcg_out32 (s, MULLW | TAB (0, args[2], args[3]));
1685
            tcg_out32 (s, MULHWU | TAB (args[1], args[2], args[3]));
1686
            tcg_out_mov (s, TCG_TYPE_I32, args[0], 0);
1687
        }
1688
        else {
1689
            tcg_out32 (s, MULLW | TAB (args[0], args[2], args[3]));
1690
            tcg_out32 (s, MULHWU | TAB (args[1], args[2], args[3]));
1691
        }
1692
        break;
1693

    
1694
    case INDEX_op_shl_i32:
1695
        if (const_args[2]) {
1696
            tcg_out32 (s, (RLWINM
1697
                           | RA (args[0])
1698
                           | RS (args[1])
1699
                           | SH (args[2])
1700
                           | MB (0)
1701
                           | ME (31 - args[2])
1702
                           )
1703
                );
1704
        }
1705
        else
1706
            tcg_out32 (s, SLW | SAB (args[1], args[0], args[2]));
1707
        break;
1708
    case INDEX_op_shr_i32:
1709
        if (const_args[2]) {
1710
            tcg_out32 (s, (RLWINM
1711
                           | RA (args[0])
1712
                           | RS (args[1])
1713
                           | SH (32 - args[2])
1714
                           | MB (args[2])
1715
                           | ME (31)
1716
                           )
1717
                );
1718
        }
1719
        else
1720
            tcg_out32 (s, SRW | SAB (args[1], args[0], args[2]));
1721
        break;
1722
    case INDEX_op_sar_i32:
1723
        if (const_args[2])
1724
            tcg_out32 (s, SRAWI | RS (args[1]) | RA (args[0]) | SH (args[2]));
1725
        else
1726
            tcg_out32 (s, SRAW | SAB (args[1], args[0], args[2]));
1727
        break;
1728
    case INDEX_op_rotl_i32:
1729
        {
1730
            int op = 0
1731
                | RA (args[0])
1732
                | RS (args[1])
1733
                | MB (0)
1734
                | ME (31)
1735
                | (const_args[2] ? RLWINM | SH (args[2])
1736
                                 : RLWNM | RB (args[2]))
1737
                ;
1738
            tcg_out32 (s, op);
1739
        }
1740
        break;
1741
    case INDEX_op_rotr_i32:
1742
        if (const_args[2]) {
1743
            if (!args[2]) {
1744
                tcg_out_mov (s, TCG_TYPE_I32, args[0], args[1]);
1745
            }
1746
            else {
1747
                tcg_out32 (s, RLWINM
1748
                           | RA (args[0])
1749
                           | RS (args[1])
1750
                           | SH (32 - args[2])
1751
                           | MB (0)
1752
                           | ME (31)
1753
                    );
1754
            }
1755
        }
1756
        else {
1757
            tcg_out32 (s, SUBFIC | RT (0) | RA (args[2]) | 32);
1758
            tcg_out32 (s, RLWNM
1759
                       | RA (args[0])
1760
                       | RS (args[1])
1761
                       | RB (0)
1762
                       | MB (0)
1763
                       | ME (31)
1764
                );
1765
        }
1766
        break;
1767

    
1768
    case INDEX_op_add2_i32:
1769
        if (args[0] == args[3] || args[0] == args[5]) {
1770
            tcg_out32 (s, ADDC | TAB (0, args[2], args[4]));
1771
            tcg_out32 (s, ADDE | TAB (args[1], args[3], args[5]));
1772
            tcg_out_mov (s, TCG_TYPE_I32, args[0], 0);
1773
        }
1774
        else {
1775
            tcg_out32 (s, ADDC | TAB (args[0], args[2], args[4]));
1776
            tcg_out32 (s, ADDE | TAB (args[1], args[3], args[5]));
1777
        }
1778
        break;
1779
    case INDEX_op_sub2_i32:
1780
        if (args[0] == args[3] || args[0] == args[5]) {
1781
            tcg_out32 (s, SUBFC | TAB (0, args[4], args[2]));
1782
            tcg_out32 (s, SUBFE | TAB (args[1], args[5], args[3]));
1783
            tcg_out_mov (s, TCG_TYPE_I32, args[0], 0);
1784
        }
1785
        else {
1786
            tcg_out32 (s, SUBFC | TAB (args[0], args[4], args[2]));
1787
            tcg_out32 (s, SUBFE | TAB (args[1], args[5], args[3]));
1788
        }
1789
        break;
1790

    
1791
    case INDEX_op_brcond_i32:
1792
        /*
1793
          args[0] = r0
1794
          args[1] = r1
1795
          args[2] = cond
1796
          args[3] = r1 is const
1797
          args[4] = label_index
1798
        */
1799
        tcg_out_brcond (s, args[2], args[0], args[1], const_args[1], args[3]);
1800
        break;
1801
    case INDEX_op_brcond2_i32:
1802
        tcg_out_brcond2(s, args, const_args);
1803
        break;
1804

    
1805
    case INDEX_op_neg_i32:
1806
        tcg_out32 (s, NEG | RT (args[0]) | RA (args[1]));
1807
        break;
1808

    
1809
    case INDEX_op_not_i32:
1810
        tcg_out32 (s, NOR | SAB (args[1], args[0], args[1]));
1811
        break;
1812

    
1813
    case INDEX_op_qemu_ld8u:
1814
        tcg_out_qemu_ld(s, args, 0);
1815
        break;
1816
    case INDEX_op_qemu_ld8s:
1817
        tcg_out_qemu_ld(s, args, 0 | 4);
1818
        break;
1819
    case INDEX_op_qemu_ld16u:
1820
        tcg_out_qemu_ld(s, args, 1);
1821
        break;
1822
    case INDEX_op_qemu_ld16s:
1823
        tcg_out_qemu_ld(s, args, 1 | 4);
1824
        break;
1825
    case INDEX_op_qemu_ld32:
1826
        tcg_out_qemu_ld(s, args, 2);
1827
        break;
1828
    case INDEX_op_qemu_ld64:
1829
        tcg_out_qemu_ld(s, args, 3);
1830
        break;
1831
    case INDEX_op_qemu_st8:
1832
        tcg_out_qemu_st(s, args, 0);
1833
        break;
1834
    case INDEX_op_qemu_st16:
1835
        tcg_out_qemu_st(s, args, 1);
1836
        break;
1837
    case INDEX_op_qemu_st32:
1838
        tcg_out_qemu_st(s, args, 2);
1839
        break;
1840
    case INDEX_op_qemu_st64:
1841
        tcg_out_qemu_st(s, args, 3);
1842
        break;
1843

    
1844
    case INDEX_op_ext8s_i32:
1845
        tcg_out32 (s, EXTSB | RS (args[1]) | RA (args[0]));
1846
        break;
1847
    case INDEX_op_ext8u_i32:
1848
        tcg_out32 (s, RLWINM
1849
                   | RA (args[0])
1850
                   | RS (args[1])
1851
                   | SH (0)
1852
                   | MB (24)
1853
                   | ME (31)
1854
            );
1855
        break;
1856
    case INDEX_op_ext16s_i32:
1857
        tcg_out32 (s, EXTSH | RS (args[1]) | RA (args[0]));
1858
        break;
1859
    case INDEX_op_ext16u_i32:
1860
        tcg_out32 (s, RLWINM
1861
                   | RA (args[0])
1862
                   | RS (args[1])
1863
                   | SH (0)
1864
                   | MB (16)
1865
                   | ME (31)
1866
            );
1867
        break;
1868

    
1869
    case INDEX_op_setcond_i32:
1870
        tcg_out_setcond (s, args[3], args[0], args[1], args[2], const_args[2]);
1871
        break;
1872
    case INDEX_op_setcond2_i32:
1873
        tcg_out_setcond2 (s, args, const_args);
1874
        break;
1875

    
1876
    case INDEX_op_bswap16_i32:
1877
        /* Stolen from gcc's builtin_bswap16 */
1878

    
1879
        /* a1 = abcd */
1880

    
1881
        /* r0 = (a1 << 8) & 0xff00 # 00d0 */
1882
        tcg_out32 (s, RLWINM
1883
                   | RA (0)
1884
                   | RS (args[1])
1885
                   | SH (8)
1886
                   | MB (16)
1887
                   | ME (23)
1888
            );
1889

    
1890
        /* a0 = rotate_left (a1, 24) & 0xff # 000c */
1891
        tcg_out32 (s, RLWINM
1892
                   | RA (args[0])
1893
                   | RS (args[1])
1894
                   | SH (24)
1895
                   | MB (24)
1896
                   | ME (31)
1897
            );
1898

    
1899
        /* a0 = a0 | r0 # 00dc */
1900
        tcg_out32 (s, OR | SAB (0, args[0], args[0]));
1901
        break;
1902

    
1903
    case INDEX_op_bswap32_i32:
1904
        /* Stolen from gcc's builtin_bswap32 */
1905
        {
1906
            int a0 = args[0];
1907

    
1908
            /* a1 = args[1] # abcd */
1909

    
1910
            if (a0 == args[1]) {
1911
                a0 = 0;
1912
            }
1913

    
1914
            /* a0 = rotate_left (a1, 8) # bcda */
1915
            tcg_out32 (s, RLWINM
1916
                       | RA (a0)
1917
                       | RS (args[1])
1918
                       | SH (8)
1919
                       | MB (0)
1920
                       | ME (31)
1921
                );
1922

    
1923
            /* a0 = (a0 & ~0xff000000) | ((a1 << 24) & 0xff000000) # dcda */
1924
            tcg_out32 (s, RLWIMI
1925
                       | RA (a0)
1926
                       | RS (args[1])
1927
                       | SH (24)
1928
                       | MB (0)
1929
                       | ME (7)
1930
                );
1931

    
1932
            /* a0 = (a0 & ~0x0000ff00) | ((a1 << 24) & 0x0000ff00) # dcba */
1933
            tcg_out32 (s, RLWIMI
1934
                       | RA (a0)
1935
                       | RS (args[1])
1936
                       | SH (24)
1937
                       | MB (16)
1938
                       | ME (23)
1939
                );
1940

    
1941
            if (!a0) {
1942
                tcg_out_mov (s, TCG_TYPE_I32, args[0], a0);
1943
            }
1944
        }
1945
        break;
1946

    
1947
    case INDEX_op_deposit_i32:
1948
        tcg_out32 (s, RLWIMI
1949
                   | RA (args[0])
1950
                   | RS (args[2])
1951
                   | SH (args[3])
1952
                   | MB (32 - args[3] - args[4])
1953
                   | ME (31 - args[3])
1954
            );
1955
        break;
1956

    
1957
    case INDEX_op_movcond_i32:
1958
        tcg_out_movcond (s, args[5], args[0],
1959
                         args[1], args[2],
1960
                         args[3], args[4],
1961
                         const_args[2]);
1962
        break;
1963

    
1964
    default:
1965
        tcg_dump_ops (s);
1966
        tcg_abort ();
1967
    }
1968
}
1969

    
1970
static const TCGTargetOpDef ppc_op_defs[] = {
1971
    { INDEX_op_exit_tb, { } },
1972
    { INDEX_op_goto_tb, { } },
1973
    { INDEX_op_call, { "ri" } },
1974
    { INDEX_op_br, { } },
1975

    
1976
    { INDEX_op_mov_i32, { "r", "r" } },
1977
    { INDEX_op_movi_i32, { "r" } },
1978
    { INDEX_op_ld8u_i32, { "r", "r" } },
1979
    { INDEX_op_ld8s_i32, { "r", "r" } },
1980
    { INDEX_op_ld16u_i32, { "r", "r" } },
1981
    { INDEX_op_ld16s_i32, { "r", "r" } },
1982
    { INDEX_op_ld_i32, { "r", "r" } },
1983
    { INDEX_op_st8_i32, { "r", "r" } },
1984
    { INDEX_op_st16_i32, { "r", "r" } },
1985
    { INDEX_op_st_i32, { "r", "r" } },
1986

    
1987
    { INDEX_op_add_i32, { "r", "r", "ri" } },
1988
    { INDEX_op_mul_i32, { "r", "r", "ri" } },
1989
    { INDEX_op_div_i32, { "r", "r", "r" } },
1990
    { INDEX_op_divu_i32, { "r", "r", "r" } },
1991
    { INDEX_op_rem_i32, { "r", "r", "r" } },
1992
    { INDEX_op_remu_i32, { "r", "r", "r" } },
1993
    { INDEX_op_mulu2_i32, { "r", "r", "r", "r" } },
1994
    { INDEX_op_sub_i32, { "r", "r", "ri" } },
1995
    { INDEX_op_and_i32, { "r", "r", "ri" } },
1996
    { INDEX_op_or_i32, { "r", "r", "ri" } },
1997
    { INDEX_op_xor_i32, { "r", "r", "ri" } },
1998

    
1999
    { INDEX_op_shl_i32, { "r", "r", "ri" } },
2000
    { INDEX_op_shr_i32, { "r", "r", "ri" } },
2001
    { INDEX_op_sar_i32, { "r", "r", "ri" } },
2002

    
2003
    { INDEX_op_rotl_i32, { "r", "r", "ri" } },
2004
    { INDEX_op_rotr_i32, { "r", "r", "ri" } },
2005

    
2006
    { INDEX_op_brcond_i32, { "r", "ri" } },
2007

    
2008
    { INDEX_op_add2_i32, { "r", "r", "r", "r", "r", "r" } },
2009
    { INDEX_op_sub2_i32, { "r", "r", "r", "r", "r", "r" } },
2010
    { INDEX_op_brcond2_i32, { "r", "r", "r", "r" } },
2011

    
2012
    { INDEX_op_neg_i32, { "r", "r" } },
2013
    { INDEX_op_not_i32, { "r", "r" } },
2014

    
2015
    { INDEX_op_andc_i32, { "r", "r", "r" } },
2016
    { INDEX_op_orc_i32, { "r", "r", "r" } },
2017
    { INDEX_op_eqv_i32, { "r", "r", "r" } },
2018
    { INDEX_op_nand_i32, { "r", "r", "r" } },
2019
    { INDEX_op_nor_i32, { "r", "r", "r" } },
2020

    
2021
    { INDEX_op_setcond_i32, { "r", "r", "ri" } },
2022
    { INDEX_op_setcond2_i32, { "r", "r", "r", "ri", "ri" } },
2023

    
2024
    { INDEX_op_bswap16_i32, { "r", "r" } },
2025
    { INDEX_op_bswap32_i32, { "r", "r" } },
2026

    
2027
#if TARGET_LONG_BITS == 32
2028
    { INDEX_op_qemu_ld8u, { "r", "L" } },
2029
    { INDEX_op_qemu_ld8s, { "r", "L" } },
2030
    { INDEX_op_qemu_ld16u, { "r", "L" } },
2031
    { INDEX_op_qemu_ld16s, { "r", "L" } },
2032
    { INDEX_op_qemu_ld32, { "r", "L" } },
2033
    { INDEX_op_qemu_ld64, { "r", "r", "L" } },
2034

    
2035
    { INDEX_op_qemu_st8, { "K", "K" } },
2036
    { INDEX_op_qemu_st16, { "K", "K" } },
2037
    { INDEX_op_qemu_st32, { "K", "K" } },
2038
    { INDEX_op_qemu_st64, { "M", "M", "M" } },
2039
#else
2040
    { INDEX_op_qemu_ld8u, { "r", "L", "L" } },
2041
    { INDEX_op_qemu_ld8s, { "r", "L", "L" } },
2042
    { INDEX_op_qemu_ld16u, { "r", "L", "L" } },
2043
    { INDEX_op_qemu_ld16s, { "r", "L", "L" } },
2044
    { INDEX_op_qemu_ld32, { "r", "L", "L" } },
2045
    { INDEX_op_qemu_ld64, { "r", "L", "L", "L" } },
2046

    
2047
    { INDEX_op_qemu_st8, { "K", "K", "K" } },
2048
    { INDEX_op_qemu_st16, { "K", "K", "K" } },
2049
    { INDEX_op_qemu_st32, { "K", "K", "K" } },
2050
    { INDEX_op_qemu_st64, { "M", "M", "M", "M" } },
2051
#endif
2052

    
2053
    { INDEX_op_ext8s_i32, { "r", "r" } },
2054
    { INDEX_op_ext8u_i32, { "r", "r" } },
2055
    { INDEX_op_ext16s_i32, { "r", "r" } },
2056
    { INDEX_op_ext16u_i32, { "r", "r" } },
2057

    
2058
    { INDEX_op_deposit_i32, { "r", "0", "r" } },
2059
    { INDEX_op_movcond_i32, { "r", "r", "ri", "r", "r" } },
2060

    
2061
    { -1 },
2062
};
2063

    
2064
static void tcg_target_init(TCGContext *s)
2065
{
2066
    tcg_regset_set32(tcg_target_available_regs[TCG_TYPE_I32], 0, 0xffffffff);
2067
    tcg_regset_set32(tcg_target_call_clobber_regs, 0,
2068
                     (1 << TCG_REG_R0) |
2069
#ifdef TCG_TARGET_CALL_DARWIN
2070
                     (1 << TCG_REG_R2) |
2071
#endif
2072
                     (1 << TCG_REG_R3) |
2073
                     (1 << TCG_REG_R4) |
2074
                     (1 << TCG_REG_R5) |
2075
                     (1 << TCG_REG_R6) |
2076
                     (1 << TCG_REG_R7) |
2077
                     (1 << TCG_REG_R8) |
2078
                     (1 << TCG_REG_R9) |
2079
                     (1 << TCG_REG_R10) |
2080
                     (1 << TCG_REG_R11) |
2081
                     (1 << TCG_REG_R12)
2082
        );
2083

    
2084
    tcg_regset_clear(s->reserved_regs);
2085
    tcg_regset_set_reg(s->reserved_regs, TCG_REG_R0);
2086
    tcg_regset_set_reg(s->reserved_regs, TCG_REG_R1);
2087
#ifndef TCG_TARGET_CALL_DARWIN
2088
    tcg_regset_set_reg(s->reserved_regs, TCG_REG_R2);
2089
#endif
2090
#ifdef _CALL_SYSV
2091
    tcg_regset_set_reg(s->reserved_regs, TCG_REG_R13);
2092
#endif
2093

    
2094
    tcg_add_target_add_op_defs(ppc_op_defs);
2095
}