Revision f02ca5cb
b/tcg/sparc/tcg-target.c | ||
---|---|---|
134 | 134 |
return 0; |
135 | 135 |
} |
136 | 136 |
|
137 |
#define ABS(x) ((x) < 0? -(x) : (x)) |
|
137 |
static inline int check_fit(tcg_target_long val, unsigned int bits) |
|
138 |
{ |
|
139 |
return ((val << ((sizeof(tcg_target_long) * 8 - bits)) |
|
140 |
>> (sizeof(tcg_target_long) * 8 - bits)) == val); |
|
141 |
} |
|
142 |
|
|
138 | 143 |
/* test if a constant matches the constraint */ |
139 | 144 |
static inline int tcg_target_const_match(tcg_target_long val, |
140 | 145 |
const TCGArgConstraint *arg_ct) |
... | ... | |
144 | 149 |
ct = arg_ct->ct; |
145 | 150 |
if (ct & TCG_CT_CONST) |
146 | 151 |
return 1; |
147 |
else if ((ct & TCG_CT_CONST_S11) && ABS(val) == (ABS(val) & 0x3ff))
|
|
152 |
else if ((ct & TCG_CT_CONST_S11) && check_fit(val, 11))
|
|
148 | 153 |
return 1; |
149 |
else if ((ct & TCG_CT_CONST_S13) && ABS(val) == (ABS(val) & 0xfff))
|
|
154 |
else if ((ct & TCG_CT_CONST_S13) && check_fit(val, 13))
|
|
150 | 155 |
return 1; |
151 | 156 |
else |
152 | 157 |
return 0; |
... | ... | |
217 | 222 |
int ret, tcg_target_long arg) |
218 | 223 |
{ |
219 | 224 |
#if defined(__sparc_v9__) && !defined(__sparc_v8plus__) |
220 |
if (arg != (arg & 0xffffffff))
|
|
225 |
if (!check_fit(arg, 32))
|
|
221 | 226 |
fprintf(stderr, "unimplemented %s with constant %ld\n", __func__, arg); |
222 | 227 |
#endif |
223 |
if (arg == (arg & 0xfff))
|
|
228 |
if (check_fit(arg, 13))
|
|
224 | 229 |
tcg_out32(s, ARITH_OR | INSN_RD(ret) | INSN_RS1(TCG_REG_G0) | |
225 | 230 |
INSN_IMM13(arg)); |
226 | 231 |
else { |
... | ... | |
243 | 248 |
tcg_target_long arg) |
244 | 249 |
{ |
245 | 250 |
#if defined(__sparc_v9__) && !defined(__sparc_v8plus__) |
246 |
if (arg != (arg & 0xffffffff))
|
|
251 |
if (!check_fit(arg, 32))
|
|
247 | 252 |
fprintf(stderr, "unimplemented %s with offset %ld\n", __func__, arg); |
248 |
if (arg != (arg & 0xfff))
|
|
253 |
if (!check_fit(arg, 13))
|
|
249 | 254 |
tcg_out32(s, SETHI | INSN_RD(ret) | (((uint32_t)arg & 0xfffffc00) >> 10)); |
250 | 255 |
tcg_out32(s, LDX | INSN_RD(ret) | INSN_RS1(ret) | |
251 | 256 |
INSN_IMM13(arg & 0x3ff)); |
... | ... | |
256 | 261 |
|
257 | 262 |
static inline void tcg_out_ldst(TCGContext *s, int ret, int addr, int offset, int op) |
258 | 263 |
{ |
259 |
if (offset == (offset & 0xfff))
|
|
264 |
if (check_fit(offset, 13))
|
|
260 | 265 |
tcg_out32(s, op | INSN_RD(ret) | INSN_RS1(addr) | |
261 | 266 |
INSN_IMM13(offset)); |
262 | 267 |
else |
... | ... | |
306 | 311 |
static inline void tcg_out_addi(TCGContext *s, int reg, tcg_target_long val) |
307 | 312 |
{ |
308 | 313 |
if (val != 0) { |
309 |
if (val == (val & 0xfff))
|
|
314 |
if (check_fit(val, 13))
|
|
310 | 315 |
tcg_out_arithi(s, reg, reg, val, ARITH_ADD); |
311 | 316 |
else |
312 | 317 |
fprintf(stderr, "unimplemented addi %ld\n", (long)val); |
... | ... | |
344 | 349 |
case INDEX_op_goto_tb: |
345 | 350 |
if (s->tb_jmp_offset) { |
346 | 351 |
/* direct jump method */ |
347 |
if (ABS(args[0] - (unsigned long)s->code_ptr) == |
|
348 |
(ABS(args[0] - (unsigned long)s->code_ptr) & 0x1fffff)) { |
|
352 |
if (check_fit(args[0] - (unsigned long)s->code_ptr, 26)) { |
|
349 | 353 |
tcg_out32(s, BA | |
350 | 354 |
INSN_OFF22(args[0] - (unsigned long)s->code_ptr)); |
351 | 355 |
} else { |
Also available in: Unified diff