~jderose/ubuntu/raring/qemu/vde-again

« back to all changes in this revision

Viewing changes to target-i386/helper_template.h

  • Committer: Bazaar Package Importer
  • Author(s): Aurelien Jarno, Aurelien Jarno
  • Date: 2009-03-22 10:13:17 UTC
  • mfrom: (1.2.1 upstream) (6.1.1 sid)
  • Revision ID: james.westby@ubuntu.com-20090322101317-iigjtnu5qil35dtb
Tags: 0.10.1-1
[ Aurelien Jarno ]
* New upstream stable release:
  - patches/80_stable-branch.patch: remove.
* debian/control: 
  - Remove depends on proll.
  - Move depends on device-tree-compiler to build-depends.
  - Bump Standards-Version to 3.8.1 (no changes).
* patches/82_qemu-img_decimal.patch: new patch from upstream to make
  qemu-img accept sizes with decimal values (closes: bug#501400).

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 *  i386 helpers
 
3
 *
 
4
 *  Copyright (c) 2008 Fabrice Bellard
 
5
 *
 
6
 * This library is free software; you can redistribute it and/or
 
7
 * modify it under the terms of the GNU Lesser General Public
 
8
 * License as published by the Free Software Foundation; either
 
9
 * version 2 of the License, or (at your option) any later version.
 
10
 *
 
11
 * This library is distributed in the hope that it will be useful,
 
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 
14
 * Lesser General Public License for more details.
 
15
 *
 
16
 * You should have received a copy of the GNU Lesser General Public
 
17
 * License along with this library; if not, write to the Free Software
 
18
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA  02110-1301 USA
 
19
 */
 
20
#define DATA_BITS (1 << (3 + SHIFT))
 
21
#define SHIFT_MASK (DATA_BITS - 1)
 
22
#define SIGN_MASK (((target_ulong)1) << (DATA_BITS - 1))
 
23
#if DATA_BITS <= 32
 
24
#define SHIFT1_MASK 0x1f
 
25
#else
 
26
#define SHIFT1_MASK 0x3f
 
27
#endif
 
28
 
 
29
#if DATA_BITS == 8
 
30
#define SUFFIX b
 
31
#define DATA_TYPE uint8_t
 
32
#define DATA_STYPE int8_t
 
33
#define DATA_MASK 0xff
 
34
#elif DATA_BITS == 16
 
35
#define SUFFIX w
 
36
#define DATA_TYPE uint16_t
 
37
#define DATA_STYPE int16_t
 
38
#define DATA_MASK 0xffff
 
39
#elif DATA_BITS == 32
 
40
#define SUFFIX l
 
41
#define DATA_TYPE uint32_t
 
42
#define DATA_STYPE int32_t
 
43
#define DATA_MASK 0xffffffff
 
44
#elif DATA_BITS == 64
 
45
#define SUFFIX q
 
46
#define DATA_TYPE uint64_t
 
47
#define DATA_STYPE int64_t
 
48
#define DATA_MASK 0xffffffffffffffffULL
 
49
#else
 
50
#error unhandled operand size
 
51
#endif
 
52
 
 
53
/* dynamic flags computation */
 
54
 
 
55
static int glue(compute_all_add, SUFFIX)(void)
 
56
{
 
57
    int cf, pf, af, zf, sf, of;
 
58
    target_long src1, src2;
 
59
    src1 = CC_SRC;
 
60
    src2 = CC_DST - CC_SRC;
 
61
    cf = (DATA_TYPE)CC_DST < (DATA_TYPE)src1;
 
62
    pf = parity_table[(uint8_t)CC_DST];
 
63
    af = (CC_DST ^ src1 ^ src2) & 0x10;
 
64
    zf = ((DATA_TYPE)CC_DST == 0) << 6;
 
65
    sf = lshift(CC_DST, 8 - DATA_BITS) & 0x80;
 
66
    of = lshift((src1 ^ src2 ^ -1) & (src1 ^ CC_DST), 12 - DATA_BITS) & CC_O;
 
67
    return cf | pf | af | zf | sf | of;
 
68
}
 
69
 
 
70
static int glue(compute_c_add, SUFFIX)(void)
 
71
{
 
72
    int cf;
 
73
    target_long src1;
 
74
    src1 = CC_SRC;
 
75
    cf = (DATA_TYPE)CC_DST < (DATA_TYPE)src1;
 
76
    return cf;
 
77
}
 
78
 
 
79
static int glue(compute_all_adc, SUFFIX)(void)
 
80
{
 
81
    int cf, pf, af, zf, sf, of;
 
82
    target_long src1, src2;
 
83
    src1 = CC_SRC;
 
84
    src2 = CC_DST - CC_SRC - 1;
 
85
    cf = (DATA_TYPE)CC_DST <= (DATA_TYPE)src1;
 
86
    pf = parity_table[(uint8_t)CC_DST];
 
87
    af = (CC_DST ^ src1 ^ src2) & 0x10;
 
88
    zf = ((DATA_TYPE)CC_DST == 0) << 6;
 
89
    sf = lshift(CC_DST, 8 - DATA_BITS) & 0x80;
 
90
    of = lshift((src1 ^ src2 ^ -1) & (src1 ^ CC_DST), 12 - DATA_BITS) & CC_O;
 
91
    return cf | pf | af | zf | sf | of;
 
92
}
 
93
 
 
94
static int glue(compute_c_adc, SUFFIX)(void)
 
95
{
 
96
    int cf;
 
97
    target_long src1;
 
98
    src1 = CC_SRC;
 
99
    cf = (DATA_TYPE)CC_DST <= (DATA_TYPE)src1;
 
100
    return cf;
 
101
}
 
102
 
 
103
static int glue(compute_all_sub, SUFFIX)(void)
 
104
{
 
105
    int cf, pf, af, zf, sf, of;
 
106
    target_long src1, src2;
 
107
    src1 = CC_DST + CC_SRC;
 
108
    src2 = CC_SRC;
 
109
    cf = (DATA_TYPE)src1 < (DATA_TYPE)src2;
 
110
    pf = parity_table[(uint8_t)CC_DST];
 
111
    af = (CC_DST ^ src1 ^ src2) & 0x10;
 
112
    zf = ((DATA_TYPE)CC_DST == 0) << 6;
 
113
    sf = lshift(CC_DST, 8 - DATA_BITS) & 0x80;
 
114
    of = lshift((src1 ^ src2) & (src1 ^ CC_DST), 12 - DATA_BITS) & CC_O;
 
115
    return cf | pf | af | zf | sf | of;
 
116
}
 
117
 
 
118
static int glue(compute_c_sub, SUFFIX)(void)
 
119
{
 
120
    int cf;
 
121
    target_long src1, src2;
 
122
    src1 = CC_DST + CC_SRC;
 
123
    src2 = CC_SRC;
 
124
    cf = (DATA_TYPE)src1 < (DATA_TYPE)src2;
 
125
    return cf;
 
126
}
 
127
 
 
128
static int glue(compute_all_sbb, SUFFIX)(void)
 
129
{
 
130
    int cf, pf, af, zf, sf, of;
 
131
    target_long src1, src2;
 
132
    src1 = CC_DST + CC_SRC + 1;
 
133
    src2 = CC_SRC;
 
134
    cf = (DATA_TYPE)src1 <= (DATA_TYPE)src2;
 
135
    pf = parity_table[(uint8_t)CC_DST];
 
136
    af = (CC_DST ^ src1 ^ src2) & 0x10;
 
137
    zf = ((DATA_TYPE)CC_DST == 0) << 6;
 
138
    sf = lshift(CC_DST, 8 - DATA_BITS) & 0x80;
 
139
    of = lshift((src1 ^ src2) & (src1 ^ CC_DST), 12 - DATA_BITS) & CC_O;
 
140
    return cf | pf | af | zf | sf | of;
 
141
}
 
142
 
 
143
static int glue(compute_c_sbb, SUFFIX)(void)
 
144
{
 
145
    int cf;
 
146
    target_long src1, src2;
 
147
    src1 = CC_DST + CC_SRC + 1;
 
148
    src2 = CC_SRC;
 
149
    cf = (DATA_TYPE)src1 <= (DATA_TYPE)src2;
 
150
    return cf;
 
151
}
 
152
 
 
153
static int glue(compute_all_logic, SUFFIX)(void)
 
154
{
 
155
    int cf, pf, af, zf, sf, of;
 
156
    cf = 0;
 
157
    pf = parity_table[(uint8_t)CC_DST];
 
158
    af = 0;
 
159
    zf = ((DATA_TYPE)CC_DST == 0) << 6;
 
160
    sf = lshift(CC_DST, 8 - DATA_BITS) & 0x80;
 
161
    of = 0;
 
162
    return cf | pf | af | zf | sf | of;
 
163
}
 
164
 
 
165
static int glue(compute_c_logic, SUFFIX)(void)
 
166
{
 
167
    return 0;
 
168
}
 
169
 
 
170
static int glue(compute_all_inc, SUFFIX)(void)
 
171
{
 
172
    int cf, pf, af, zf, sf, of;
 
173
    target_long src1, src2;
 
174
    src1 = CC_DST - 1;
 
175
    src2 = 1;
 
176
    cf = CC_SRC;
 
177
    pf = parity_table[(uint8_t)CC_DST];
 
178
    af = (CC_DST ^ src1 ^ src2) & 0x10;
 
179
    zf = ((DATA_TYPE)CC_DST == 0) << 6;
 
180
    sf = lshift(CC_DST, 8 - DATA_BITS) & 0x80;
 
181
    of = ((CC_DST & DATA_MASK) == SIGN_MASK) << 11;
 
182
    return cf | pf | af | zf | sf | of;
 
183
}
 
184
 
 
185
#if DATA_BITS == 32
 
186
static int glue(compute_c_inc, SUFFIX)(void)
 
187
{
 
188
    return CC_SRC;
 
189
}
 
190
#endif
 
191
 
 
192
static int glue(compute_all_dec, SUFFIX)(void)
 
193
{
 
194
    int cf, pf, af, zf, sf, of;
 
195
    target_long src1, src2;
 
196
    src1 = CC_DST + 1;
 
197
    src2 = 1;
 
198
    cf = CC_SRC;
 
199
    pf = parity_table[(uint8_t)CC_DST];
 
200
    af = (CC_DST ^ src1 ^ src2) & 0x10;
 
201
    zf = ((DATA_TYPE)CC_DST == 0) << 6;
 
202
    sf = lshift(CC_DST, 8 - DATA_BITS) & 0x80;
 
203
    of = ((CC_DST & DATA_MASK) == ((target_ulong)SIGN_MASK - 1)) << 11;
 
204
    return cf | pf | af | zf | sf | of;
 
205
}
 
206
 
 
207
static int glue(compute_all_shl, SUFFIX)(void)
 
208
{
 
209
    int cf, pf, af, zf, sf, of;
 
210
    cf = (CC_SRC >> (DATA_BITS - 1)) & CC_C;
 
211
    pf = parity_table[(uint8_t)CC_DST];
 
212
    af = 0; /* undefined */
 
213
    zf = ((DATA_TYPE)CC_DST == 0) << 6;
 
214
    sf = lshift(CC_DST, 8 - DATA_BITS) & 0x80;
 
215
    /* of is defined if shift count == 1 */
 
216
    of = lshift(CC_SRC ^ CC_DST, 12 - DATA_BITS) & CC_O;
 
217
    return cf | pf | af | zf | sf | of;
 
218
}
 
219
 
 
220
static int glue(compute_c_shl, SUFFIX)(void)
 
221
{
 
222
    return (CC_SRC >> (DATA_BITS - 1)) & CC_C;
 
223
}
 
224
 
 
225
#if DATA_BITS == 32
 
226
static int glue(compute_c_sar, SUFFIX)(void)
 
227
{
 
228
    return CC_SRC & 1;
 
229
}
 
230
#endif
 
231
 
 
232
static int glue(compute_all_sar, SUFFIX)(void)
 
233
{
 
234
    int cf, pf, af, zf, sf, of;
 
235
    cf = CC_SRC & 1;
 
236
    pf = parity_table[(uint8_t)CC_DST];
 
237
    af = 0; /* undefined */
 
238
    zf = ((DATA_TYPE)CC_DST == 0) << 6;
 
239
    sf = lshift(CC_DST, 8 - DATA_BITS) & 0x80;
 
240
    /* of is defined if shift count == 1 */
 
241
    of = lshift(CC_SRC ^ CC_DST, 12 - DATA_BITS) & CC_O;
 
242
    return cf | pf | af | zf | sf | of;
 
243
}
 
244
 
 
245
#if DATA_BITS == 32
 
246
static int glue(compute_c_mul, SUFFIX)(void)
 
247
{
 
248
    int cf;
 
249
    cf = (CC_SRC != 0);
 
250
    return cf;
 
251
}
 
252
#endif
 
253
 
 
254
/* NOTE: we compute the flags like the P4. On olders CPUs, only OF and
 
255
   CF are modified and it is slower to do that. */
 
256
static int glue(compute_all_mul, SUFFIX)(void)
 
257
{
 
258
    int cf, pf, af, zf, sf, of;
 
259
    cf = (CC_SRC != 0);
 
260
    pf = parity_table[(uint8_t)CC_DST];
 
261
    af = 0; /* undefined */
 
262
    zf = ((DATA_TYPE)CC_DST == 0) << 6;
 
263
    sf = lshift(CC_DST, 8 - DATA_BITS) & 0x80;
 
264
    of = cf << 11;
 
265
    return cf | pf | af | zf | sf | of;
 
266
}
 
267
 
 
268
/* shifts */
 
269
 
 
270
target_ulong glue(helper_rcl, SUFFIX)(target_ulong t0, target_ulong t1)
 
271
{
 
272
    int count, eflags;
 
273
    target_ulong src;
 
274
    target_long res;
 
275
 
 
276
    count = t1 & SHIFT1_MASK;
 
277
#if DATA_BITS == 16
 
278
    count = rclw_table[count];
 
279
#elif DATA_BITS == 8
 
280
    count = rclb_table[count];
 
281
#endif
 
282
    if (count) {
 
283
        eflags = helper_cc_compute_all(CC_OP);
 
284
        t0 &= DATA_MASK;
 
285
        src = t0;
 
286
        res = (t0 << count) | ((target_ulong)(eflags & CC_C) << (count - 1));
 
287
        if (count > 1)
 
288
            res |= t0 >> (DATA_BITS + 1 - count);
 
289
        t0 = res;
 
290
        env->cc_tmp = (eflags & ~(CC_C | CC_O)) |
 
291
            (lshift(src ^ t0, 11 - (DATA_BITS - 1)) & CC_O) |
 
292
            ((src >> (DATA_BITS - count)) & CC_C);
 
293
    } else {
 
294
        env->cc_tmp = -1;
 
295
    }
 
296
    return t0;
 
297
}
 
298
 
 
299
target_ulong glue(helper_rcr, SUFFIX)(target_ulong t0, target_ulong t1)
 
300
{
 
301
    int count, eflags;
 
302
    target_ulong src;
 
303
    target_long res;
 
304
 
 
305
    count = t1 & SHIFT1_MASK;
 
306
#if DATA_BITS == 16
 
307
    count = rclw_table[count];
 
308
#elif DATA_BITS == 8
 
309
    count = rclb_table[count];
 
310
#endif
 
311
    if (count) {
 
312
        eflags = helper_cc_compute_all(CC_OP);
 
313
        t0 &= DATA_MASK;
 
314
        src = t0;
 
315
        res = (t0 >> count) | ((target_ulong)(eflags & CC_C) << (DATA_BITS - count));
 
316
        if (count > 1)
 
317
            res |= t0 << (DATA_BITS + 1 - count);
 
318
        t0 = res;
 
319
        env->cc_tmp = (eflags & ~(CC_C | CC_O)) |
 
320
            (lshift(src ^ t0, 11 - (DATA_BITS - 1)) & CC_O) |
 
321
            ((src >> (count - 1)) & CC_C);
 
322
    } else {
 
323
        env->cc_tmp = -1;
 
324
    }
 
325
    return t0;
 
326
}
 
327
 
 
328
#undef DATA_BITS
 
329
#undef SHIFT_MASK
 
330
#undef SHIFT1_MASK
 
331
#undef SIGN_MASK
 
332
#undef DATA_TYPE
 
333
#undef DATA_STYPE
 
334
#undef DATA_MASK
 
335
#undef SUFFIX