Remove ia32_l_Setcc and remove set creation callback from ir_lower_mode_b().
[libfirm] / ir / be / ia32 / ia32_spec.pl
1 # Creation: 2005/10/19
2 # $Id$
3 # This is the specification for the ia32 assembler Firm-operations
4
5 $arch = "ia32";
6
7 # register types:
8 $normal      =  0; # no special type
9 $ignore      =  1; # ignore (do not assign this register)
10 $arbitrary   =  2; # emitter can choose an arbitrary register of this class
11 $virtual     =  4; # the register is a virtual one
12 $state       =  8; # register represents a state
13 # NOTE: Last entry of each class is the largest Firm-Mode a register can hold
14 %reg_classes = (
15         gp => [
16                 { name => "edx" },
17                 { name => "ecx" },
18                 { name => "eax" },
19                 { name => "ebx" },
20                 { name => "esi" },
21                 { name => "edi" },
22                 { name => "ebp" },
23                 { name => "esp", type => $ignore },
24                 { name => "gp_NOREG", type => $ignore | $arbitrary | $virtual }, # we need a dummy register for NoReg nodes
25                 { mode => "mode_Iu" }
26         ],
27         mmx => [
28                 { name => "mm0", type => $ignore },
29                 { name => "mm1", type => $ignore },
30                 { name => "mm2", type => $ignore },
31                 { name => "mm3", type => $ignore },
32                 { name => "mm4", type => $ignore },
33                 { name => "mm5", type => $ignore },
34                 { name => "mm6", type => $ignore },
35                 { name => "mm7", type => $ignore },
36                 { mode => "mode_E", flags => "manual_ra" }
37         ],
38         xmm => [
39                 { name => "xmm0" },
40                 { name => "xmm1" },
41                 { name => "xmm2" },
42                 { name => "xmm3" },
43                 { name => "xmm4" },
44                 { name => "xmm5" },
45                 { name => "xmm6" },
46                 { name => "xmm7" },
47                 { name => "xmm_NOREG", type => $ignore | $virtual },     # we need a dummy register for NoReg nodes
48                 { mode => "mode_E" }
49         ],
50         vfp => [
51                 { name => "vf0" },
52                 { name => "vf1" },
53                 { name => "vf2" },
54                 { name => "vf3" },
55                 { name => "vf4" },
56                 { name => "vf5" },
57                 { name => "vf6" },
58                 { name => "vf7" },
59                 { name => "vfp_NOREG", type => $ignore | $arbitrary | $virtual }, # we need a dummy register for NoReg nodes
60                 { mode => "mode_E" }
61         ],
62         st => [
63                 { name => "st0", realname => "st",    type => $ignore },
64                 { name => "st1", realname => "st(1)", type => $ignore },
65                 { name => "st2", realname => "st(2)", type => $ignore },
66                 { name => "st3", realname => "st(3)", type => $ignore },
67                 { name => "st4", realname => "st(4)", type => $ignore },
68                 { name => "st5", realname => "st(5)", type => $ignore },
69                 { name => "st6", realname => "st(6)", type => $ignore },
70                 { name => "st7", realname => "st(7)", type => $ignore },
71                 { mode => "mode_E", flags => "manual_ra" }
72         ],
73         fp_cw => [      # the floating point control word
74                 { name => "fpcw", type => $ignore | $state },
75                 { mode => "ia32_mode_fpcw", flags => "manual_ra|state" }
76         ],
77         flags => [
78                 { name => "eflags", type => 0 },
79                 { mode => "mode_Iu", flags => "manual_ra" }
80         ],
81 ); # %reg_classes
82
83 %cpu = (
84         GP     => [ 1, "GP_EAX", "GP_EBX", "GP_ECX", "GP_EDX", "GP_ESI", "GP_EDI", "GP_EBP" ],
85         SSE    => [ 1, "SSE_XMM0", "SSE_XMM1", "SSE_XMM2", "SSE_XMM3", "SSE_XMM4", "SSE_XMM5", "SSE_XMM6", "SSE_XMM7" ],
86         VFP    => [ 1, "VFP_VF0", "VFP_VF1", "VFP_VF2", "VFP_VF3", "VFP_VF4", "VFP_VF5", "VFP_VF6", "VFP_VF7" ],
87         BRANCH => [ 1, "BRANCH1", "BRANCH2" ],
88 ); # %cpu
89
90 %vliw = (
91         bundle_size       => 1,
92         bundels_per_cycle => 1
93 ); # vliw
94
95 %emit_templates = (
96         S0 => "${arch}_emit_source_register(node, 0);",
97         S1 => "${arch}_emit_source_register(node, 1);",
98         S2 => "${arch}_emit_source_register(node, 2);",
99         S3 => "${arch}_emit_source_register(node, 3);",
100         SB0 => "${arch}_emit_8bit_source_register_or_immediate(node, 0);",
101         SB1 => "${arch}_emit_8bit_source_register_or_immediate(node, 1);",
102         SB2 => "${arch}_emit_8bit_source_register_or_immediate(node, 2);",
103         SB3 => "${arch}_emit_8bit_source_register_or_immediate(node, 3);",
104         SH0 => "${arch}_emit_8bit_high_source_register(node, 0);",
105         SS0 => "${arch}_emit_16bit_source_register_or_immediate(node, 0);",
106         SI0 => "${arch}_emit_source_register_or_immediate(node, 0);",
107         SI1 => "${arch}_emit_source_register_or_immediate(node, 1);",
108         SI3 => "${arch}_emit_source_register_or_immediate(node, 3);",
109         D0 => "${arch}_emit_dest_register(node, 0);",
110         D1 => "${arch}_emit_dest_register(node, 1);",
111         DS0 => "${arch}_emit_dest_register_size(node, 0);",
112         DB0 => "${arch}_emit_8bit_dest_register(node, 0);",
113         X0 => "${arch}_emit_x87_register(node, 0);",
114         X1 => "${arch}_emit_x87_register(node, 1);",
115         EX => "${arch}_emit_extend_suffix(node);",
116         M  => "${arch}_emit_mode_suffix(node);",
117         XM => "${arch}_emit_x87_mode_suffix(node);",
118         XXM => "${arch}_emit_xmm_mode_suffix(node);",
119         XSD => "${arch}_emit_xmm_mode_suffix_s(node);",
120         AM => "${arch}_emit_am(node);",
121         unop3 => "${arch}_emit_unop(node, n_ia32_unary_op);",
122         unop4 => "${arch}_emit_unop(node, n_ia32_binary_right);",
123         binop => "${arch}_emit_binop(node);",
124         x87_binop => "${arch}_emit_x87_binop(node);",
125         CMP3  => "${arch}_emit_cmp_suffix_node(node, 3);",
126 );
127
128
129
130
131 $default_op_attr_type = "ia32_op_attr_t";
132 $default_attr_type    = "ia32_attr_t";
133 $default_copy_attr    = "ia32_copy_attr";
134
135 sub ia32_custom_init_attr {
136         my $constr = shift;
137         my $node   = shift;
138         my $name   = shift;
139         my $res    = "";
140
141         if(defined($node->{modified_flags})) {
142                 $res .= "\tarch_add_irn_flags(res, arch_irn_flags_modify_flags);\n";
143         }
144         if(defined($node->{am})) {
145                 my $am = $node->{am};
146                 if($am eq "source,unary") {
147                         $res .= "\tset_ia32_am_support(res, ia32_am_unary);";
148                 } elsif($am eq "source,binary") {
149                         $res .= "\tset_ia32_am_support(res, ia32_am_binary);";
150                 } elsif($am eq "none") {
151                         # nothing to do
152                 } else {
153                         die("Invalid address mode '$am' specified on op $name");
154                 }
155                 if($am ne "none") {
156                         if($node->{state} ne "exc_pinned"
157                                         and $node->{state} ne "pinned") {
158                                 die("AM nodes must have pinned or AM pinned state ($name)");
159                         }
160                 }
161         }
162         return $res;
163 }
164 $custom_init_attr_func = \&ia32_custom_init_attr;
165
166 %init_attr = (
167         ia32_asm_attr_t =>
168                 "\tinit_ia32_attributes(res, irn_flags_, in_reqs, exec_units, n_res);\n".
169                 "\tinit_ia32_x87_attributes(res);".
170                 "\tinit_ia32_asm_attributes(res);",
171         ia32_attr_t     =>
172                 "\tinit_ia32_attributes(res, irn_flags_, in_reqs, exec_units, n_res);",
173         ia32_call_attr_t =>
174                 "\tinit_ia32_attributes(res, irn_flags_, in_reqs, exec_units, n_res);\n".
175                 "\tinit_ia32_call_attributes(res, pop, call_tp);",
176         ia32_condcode_attr_t =>
177                 "\tinit_ia32_attributes(res, irn_flags_, in_reqs, exec_units, n_res);\n".
178                 "\tinit_ia32_condcode_attributes(res, condition_code);",
179         ia32_switch_attr_t =>
180                 "\tinit_ia32_attributes(res, irn_flags_, in_reqs, exec_units, n_res);\n".
181                 "\tinit_ia32_switch_attributes(res, default_pn);",
182         ia32_copyb_attr_t =>
183                 "\tinit_ia32_attributes(res, irn_flags_, in_reqs, exec_units, n_res);\n".
184                 "\tinit_ia32_copyb_attributes(res, size);",
185         ia32_immediate_attr_t =>
186                 "\tinit_ia32_attributes(res, irn_flags_, in_reqs, exec_units, n_res);\n".
187                 "\tinit_ia32_immediate_attributes(res, symconst, symconst_sign, no_pic_adjust, offset);",
188         ia32_x87_attr_t =>
189                 "\tinit_ia32_attributes(res, irn_flags_, in_reqs, exec_units, n_res);\n".
190                 "\tinit_ia32_x87_attributes(res);",
191         ia32_climbframe_attr_t =>
192                 "\tinit_ia32_attributes(res, irn_flags_, in_reqs, exec_units, n_res);\n".
193                 "\tinit_ia32_climbframe_attributes(res, count);",
194 );
195
196 %compare_attr = (
197         ia32_asm_attr_t        => "ia32_compare_asm_attr",
198         ia32_attr_t            => "ia32_compare_nodes_attr",
199         ia32_call_attr_t       => "ia32_compare_call_attr",
200         ia32_condcode_attr_t   => "ia32_compare_condcode_attr",
201         ia32_switch_attr_t     => "ia32_compare_switch_attr",
202         ia32_copyb_attr_t      => "ia32_compare_copyb_attr",
203         ia32_immediate_attr_t  => "ia32_compare_immediate_attr",
204         ia32_x87_attr_t        => "ia32_compare_x87_attr",
205         ia32_climbframe_attr_t => "ia32_compare_climbframe_attr",
206 );
207
208 %operands = (
209 );
210
211 $mode_xmm           = "mode_E";
212 $mode_gp            = "mode_Iu";
213 $mode_flags         = "mode_Iu";
214 $mode_fpcw          = "ia32_mode_fpcw";
215 $status_flags       = [ "CF", "PF", "AF", "ZF", "SF", "OF" ];
216 $status_flags_wo_cf = [       "PF", "AF", "ZF", "SF", "OF" ];
217 $fpcw_flags         = [ "FP_IM", "FP_DM", "FP_ZM", "FP_OM", "FP_UM", "FP_PM",
218                         "FP_PC0", "FP_PC1", "FP_RC0", "FP_RC1", "FP_X" ];
219
220 %nodes = (
221
222 Immediate => {
223         state     => "pinned",
224         op_flags  => [ "constlike" ],
225         irn_flags => [ "not_scheduled" ],
226         reg_req   => { out => [ "gp_NOREG:I" ] },
227         attr      => "ir_entity *symconst, int symconst_sign, int no_pic_adjust, long offset",
228         attr_type => "ia32_immediate_attr_t",
229         hash_func => "ia32_hash_Immediate",
230         latency   => 0,
231         mode      => $mode_gp,
232 },
233
234 Asm => {
235         mode      => "mode_T",
236         arity     => "variable",
237         out_arity => "variable",
238         attr_type => "ia32_asm_attr_t",
239         attr      => "ident *asm_text, const ia32_asm_reg_t *register_map",
240         init_attr => "attr->asm_text = asm_text;\n".
241                      "\tattr->register_map = register_map;\n",
242         latency   => 10,
243         modified_flags => $status_flags,
244 },
245
246 # "allocates" a free register
247 ProduceVal => {
248         op_flags  => [ "constlike", "cse_neutral" ],
249         irn_flags => [ "rematerializable" ],
250         reg_req   => { out => [ "gp" ] },
251         emit      => "",
252         units     => [ ],
253         latency   => 0,
254         mode      => $mode_gp,
255         cmp_attr  => "return 1;",
256 },
257
258 Add => {
259         irn_flags => [ "rematerializable" ],
260         state     => "exc_pinned",
261         reg_req   => { in  => [ "gp", "gp", "none", "gp", "gp" ],
262                        out => [ "in_r4 in_r5", "flags", "none" ] },
263         ins       => [ "base", "index", "mem", "left", "right" ],
264         outs      => [ "res", "flags", "M" ],
265         emit      => '. add%M %binop',
266         am        => "source,binary",
267         units     => [ "GP" ],
268         latency   => 1,
269         mode      => $mode_gp,
270         modified_flags => $status_flags
271 },
272
273 AddMem => {
274         irn_flags => [ "rematerializable" ],
275         state     => "exc_pinned",
276         reg_req   => { in => [ "gp", "gp", "none", "gp" ], out => [ "none" ] },
277         ins       => [ "base", "index", "mem", "val" ],
278         emit      => ". add%M %SI3, %AM",
279         units     => [ "GP" ],
280         latency   => 1,
281         mode      => "mode_M",
282         modified_flags => $status_flags
283 },
284
285 AddMem8Bit => {
286         irn_flags => [ "rematerializable" ],
287         state     => "exc_pinned",
288         reg_req   => { in => [ "gp", "gp", "none", "eax ebx ecx edx" ], out => [ "none" ] },
289         ins       => [ "base", "index", "mem", "val" ],
290         emit      => ". add%M %SB3, %AM",
291         units     => [ "GP" ],
292         latency   => 1,
293         mode      => "mode_M",
294         modified_flags => $status_flags
295 },
296
297 Adc => {
298         state     => "exc_pinned",
299         reg_req   => { in => [ "gp", "gp", "none", "gp", "gp", "flags" ],
300                        out => [ "in_r4 in_r5", "flags", "none" ] },
301         ins       => [ "base", "index", "mem", "left", "right", "eflags" ],
302         outs      => [ "res", "flags", "M" ],
303         emit      => '. adc%M %binop',
304         am        => "source,binary",
305         units     => [ "GP" ],
306         latency   => 1,
307         mode      => $mode_gp,
308         modified_flags => $status_flags
309 },
310
311 l_Add => {
312         ins       => [ "left", "right" ],
313         attr_type => "",
314         dump_func => "NULL",
315 },
316
317 l_Adc => {
318         ins       => [ "left", "right", "eflags" ],
319         attr_type => "",
320         dump_func => "NULL",
321 },
322
323 Mul => {
324         # we should not rematrialize this node. It produces 2 results and has
325         # very strict constraints
326         state     => "exc_pinned",
327         reg_req   => { in => [ "gp", "gp", "none", "eax", "gp" ],
328                        out => [ "eax", "flags", "none", "edx" ] },
329         ins       => [ "base", "index", "mem", "left", "right" ],
330         emit      => '. mul%M %unop4',
331         outs      => [ "res_low", "flags", "M", "res_high" ],
332         am        => "source,binary",
333         latency   => 10,
334         units     => [ "GP" ],
335         modified_flags => $status_flags
336 },
337
338 l_Mul => {
339         ins       => [ "left", "right" ],
340         outs      => [ "res_low", "flags", "M", "res_high" ],
341         attr_type => "",
342         dump_func => "NULL",
343 },
344
345 IMul => {
346         irn_flags => [ "rematerializable" ],
347         state     => "exc_pinned",
348         # TODO: adjust out requirements for the 3 operand form
349         # (no need for should_be_same then)
350         reg_req   => { in => [ "gp", "gp", "none", "gp", "gp" ],
351                            out => [ "in_r4 in_r5", "flags", "none" ] },
352         ins       => [ "base", "index", "mem", "left", "right" ],
353         outs      => [ "res", "flags", "M" ],
354         am        => "source,binary",
355         latency   => 5,
356         units     => [ "GP" ],
357         mode      => $mode_gp,
358         modified_flags => $status_flags
359 },
360
361 IMul1OP => {
362         irn_flags => [ "rematerializable" ],
363         state     => "exc_pinned",
364         reg_req   => { in => [ "gp", "gp", "none", "eax", "gp" ],
365                        out => [ "eax", "flags", "none", "edx" ] },
366         ins       => [ "base", "index", "mem", "left", "right" ],
367         emit      => '. imul%M %unop4',
368         outs      => [ "res_low", "flags", "M", "res_high" ],
369         am        => "source,binary",
370         latency   => 5,
371         units     => [ "GP" ],
372         modified_flags => $status_flags
373 },
374
375 l_IMul => {
376         ins       => [ "left", "right" ],
377         outs      => [ "res_low", "flags", "M", "res_high" ],
378         attr_type => "",
379         dump_func => "NULL",
380 },
381
382 And => {
383         irn_flags => [ "rematerializable" ],
384         state     => "exc_pinned",
385         reg_req   => { in => [ "gp", "gp", "none", "gp", "gp" ],
386                            out => [ "in_r4 in_r5", "flags", "none" ] },
387         ins       => [ "base", "index", "mem", "left", "right" ],
388         outs      => [ "res", "flags", "M" ],
389         am        => "source,binary",
390         emit      => '. and%M %binop',
391         units     => [ "GP" ],
392         latency   => 1,
393         mode      => $mode_gp,
394         modified_flags => $status_flags
395 },
396
397 AndMem => {
398         irn_flags => [ "rematerializable" ],
399         state     => "exc_pinned",
400         reg_req   => { in => [ "gp", "gp", "none", "gp" ], out => [ "none" ] },
401         ins       => [ "base", "index", "mem", "val" ],
402         emit      => '. and%M %SI3, %AM',
403         units     => [ "GP" ],
404         latency   => 1,
405         mode      => "mode_M",
406         modified_flags => $status_flags
407 },
408
409 AndMem8Bit => {
410         irn_flags => [ "rematerializable" ],
411         state     => "exc_pinned",
412         reg_req   => { in => [ "gp", "gp", "none",  "eax ebx ecx edx" ], out => [ "none" ] },
413         ins       => [ "base", "index", "mem", "val" ],
414         emit      => '. and%M %SB3, %AM',
415         units     => [ "GP" ],
416         latency   => 1,
417         mode      => "mode_M",
418         modified_flags => $status_flags
419 },
420
421 Or => {
422         irn_flags => [ "rematerializable" ],
423         state     => "exc_pinned",
424         reg_req   => { in => [ "gp", "gp", "none", "gp", "gp" ],
425                        out => [ "in_r4 in_r5", "flags", "none" ] },
426         ins       => [ "base", "index", "mem", "left", "right" ],
427         outs      => [ "res", "flags", "M" ],
428         am        => "source,binary",
429         emit      => '. or%M %binop',
430         units     => [ "GP" ],
431         latency   => 1,
432         mode      => $mode_gp,
433         modified_flags => $status_flags
434 },
435
436 OrMem => {
437         irn_flags => [ "rematerializable" ],
438         state     => "exc_pinned",
439         reg_req   => { in => [ "gp", "gp", "none", "gp" ], out => [ "none" ] },
440         ins       => [ "base", "index", "mem", "val" ],
441         emit      => '. or%M %SI3, %AM',
442         units     => [ "GP" ],
443         latency   => 1,
444         mode      => "mode_M",
445         modified_flags => $status_flags
446 },
447
448 OrMem8Bit => {
449         irn_flags => [ "rematerializable" ],
450         state     => "exc_pinned",
451         reg_req   => { in => [ "gp", "gp", "none", "eax ebx ecx edx" ], out => [ "none" ] },
452         ins       => [ "base", "index", "mem", "val" ],
453         emit      => '. or%M %SB3, %AM',
454         units     => [ "GP" ],
455         latency   => 1,
456         mode      => "mode_M",
457         modified_flags => $status_flags
458 },
459
460 Xor => {
461         irn_flags => [ "rematerializable" ],
462         state     => "exc_pinned",
463         reg_req   => { in => [ "gp", "gp", "none", "gp", "gp" ],
464                        out => [ "in_r4 in_r5", "flags", "none" ] },
465         ins       => [ "base", "index", "mem", "left", "right" ],
466         outs      => [ "res", "flags", "M" ],
467         am        => "source,binary",
468         emit      => '. xor%M %binop',
469         units     => [ "GP" ],
470         latency   => 1,
471         mode      => $mode_gp,
472         modified_flags => $status_flags
473 },
474
475 Xor0 => {
476         op_flags  => [ "constlike" ],
477         irn_flags => [ "rematerializable" ],
478         reg_req   => { out => [ "gp", "flags" ] },
479         outs      => [ "res", "flags" ],
480         emit      => ". xor%M %D0, %D0",
481         units     => [ "GP" ],
482         latency   => 1,
483         mode      => $mode_gp,
484         modified_flags => $status_flags
485 },
486
487 XorMem => {
488         irn_flags => [ "rematerializable" ],
489         state     => "exc_pinned",
490         reg_req   => { in => [ "gp", "gp", "none", "gp" ], out => [ "none" ] },
491         ins       => [ "base", "index", "mem", "val" ],
492         emit      => '. xor%M %SI3, %AM',
493         units     => [ "GP" ],
494         latency   => 1,
495         mode      => "mode_M",
496         modified_flags => $status_flags
497 },
498
499 XorMem8Bit => {
500         irn_flags => [ "rematerializable" ],
501         state     => "exc_pinned",
502         reg_req   => { in => [ "gp", "gp", "none", "eax ebx ecx edx" ], out => [ "none" ] },
503         ins       => [ "base", "index", "mem", "val" ],
504         emit      => '. xor%M %SB3, %AM',
505         units     => [ "GP" ],
506         latency   => 1,
507         mode      => "mode_M",
508         modified_flags => $status_flags
509 },
510
511 Sub => {
512         irn_flags => [ "rematerializable" ],
513         state     => "exc_pinned",
514         reg_req   => { in => [ "gp", "gp", "none", "gp", "gp" ],
515                        out => [ "in_r4", "flags", "none" ] },
516         ins       => [ "base", "index", "mem", "minuend", "subtrahend" ],
517         outs      => [ "res", "flags", "M" ],
518         am        => "source,binary",
519         emit      => '. sub%M %binop',
520         units     => [ "GP" ],
521         latency   => 1,
522         mode      => $mode_gp,
523         modified_flags => $status_flags
524 },
525
526 SubMem => {
527         irn_flags => [ "rematerializable" ],
528         state     => "exc_pinned",
529         reg_req   => { in => [ "gp", "gp", "none", "gp" ], out => [ "none" ] },
530         ins       => [ "base", "index", "mem", "subtrahend" ],
531         emit      => '. sub%M %SI3, %AM',
532         units     => [ "GP" ],
533         latency   => 1,
534         mode      => 'mode_M',
535         modified_flags => $status_flags
536 },
537
538 SubMem8Bit => {
539         irn_flags => [ "rematerializable" ],
540         state     => "exc_pinned",
541         reg_req   => { in => [ "gp", "gp", "none", "eax ebx ecx edx" ], out => [ "none" ] },
542         ins       => [ "base", "index", "mem", "subtrahend" ],
543         emit      => '. sub%M %SB3, %AM',
544         units     => [ "GP" ],
545         latency   => 1,
546         mode      => 'mode_M',
547         modified_flags => $status_flags
548 },
549
550 Sbb => {
551         state     => "exc_pinned",
552         reg_req   => { in => [ "gp", "gp", "none", "gp", "gp", "flags" ],
553                        out => [ "in_r4", "flags", "none" ] },
554         ins       => [ "base", "index", "mem", "minuend", "subtrahend", "eflags" ],
555         outs      => [ "res", "flags", "M" ],
556         am        => "source,binary",
557         emit      => '. sbb%M %binop',
558         units     => [ "GP" ],
559         latency   => 1,
560         mode      => $mode_gp,
561         modified_flags => $status_flags
562 },
563
564 Sbb0 => {
565         # Spiller currently fails when rematerializing flag consumers
566         # irn_flags => [ "rematerializable" ],
567         reg_req   => { in => [ "flags" ], out => [ "gp", "flags" ] },
568         outs      => [ "res", "flags" ],
569         emit      => ". sbb%M %D0, %D0",
570         units     => [ "GP" ],
571         latency   => 1,
572         mode      => $mode_gp,
573         modified_flags => $status_flags
574 },
575
576 l_Sub => {
577         ins       => [ "minuend", "subtrahend" ],
578         attr_type => "",
579         dump_func => "NULL",
580 },
581
582 l_Sbb => {
583         ins       => [ "minuend", "subtrahend", "eflags" ],
584         attr_type => "",
585         dump_func => "NULL",
586 },
587
588 IDiv => {
589         op_flags  => [ "fragile", "labeled" ],
590         state     => "exc_pinned",
591         reg_req   => { in => [ "gp", "gp", "none", "gp", "eax", "edx" ],
592                        out => [ "eax", "flags", "none", "edx", "none", "none" ] },
593         ins       => [ "base", "index", "mem", "divisor", "dividend_low", "dividend_high" ],
594         outs      => [ "div_res", "flags", "M", "mod_res", "X_regular", "X_except" ],
595         am        => "source,unary",
596         emit      => ". idiv%M %unop3",
597         latency   => 25,
598         units     => [ "GP" ],
599         modified_flags => $status_flags
600 },
601
602 Div => {
603         op_flags  => [ "fragile", "labeled" ],
604         state     => "exc_pinned",
605         reg_req   => { in => [ "gp", "gp", "none", "gp", "eax", "edx" ],
606                        out => [ "eax", "flags", "none", "edx", "none", "none" ] },
607         ins       => [ "base", "index", "mem", "divisor", "dividend_low", "dividend_high" ],
608         outs      => [ "div_res", "flags", "M", "mod_res", "X_regular", "X_except" ],
609         am        => "source,unary",
610         emit      => ". div%M %unop3",
611         latency   => 25,
612         units     => [ "GP" ],
613         modified_flags => $status_flags
614 },
615
616 Shl => {
617         irn_flags => [ "rematerializable" ],
618         reg_req   => { in => [ "gp", "ecx" ],
619                        out => [ "in_r1 !in_r2", "flags" ] },
620         ins       => [ "val", "count" ],
621         outs      => [ "res", "flags" ],
622         emit      => '. shl%M %SB1, %S0',
623         units     => [ "GP" ],
624         latency   => 1,
625         mode      => $mode_gp,
626         modified_flags => $status_flags
627 },
628
629 ShlMem => {
630         irn_flags => [ "rematerializable" ],
631         state     => "exc_pinned",
632         reg_req   => { in => [ "gp", "gp", "none", "ecx" ], out => [ "none" ] },
633         ins       => [ "base", "index", "mem", "count" ],
634         emit      => '. shl%M %SB3, %AM',
635         units     => [ "GP" ],
636         latency   => 1,
637         mode      => "mode_M",
638         modified_flags => $status_flags
639 },
640
641 ShlD => {
642         irn_flags => [ "rematerializable" ],
643         reg_req   => { in => [ "gp", "gp", "ecx" ],
644                        out => [ "in_r1 !in_r2 !in_r3", "flags" ] },
645         ins       => [ "val_high", "val_low", "count" ],
646         outs      => [ "res", "flags" ],
647         emit      => ". shld%M %SB2, %S1, %D0",
648         latency   => 6,
649         units     => [ "GP" ],
650         mode      => $mode_gp,
651         modified_flags => $status_flags
652 },
653
654 Shr => {
655         irn_flags => [ "rematerializable" ],
656         reg_req   => { in => [ "gp", "ecx" ],
657                        out => [ "in_r1 !in_r2", "flags" ] },
658         ins       => [ "val", "count" ],
659         outs      => [ "res", "flags" ],
660         emit      => '. shr%M %SB1, %S0',
661         units     => [ "GP" ],
662         mode      => $mode_gp,
663         latency   => 1,
664         modified_flags => $status_flags
665 },
666
667 ShrMem => {
668         irn_flags => [ "rematerializable" ],
669         state     => "exc_pinned",
670         reg_req   => { in => [ "gp", "gp", "none", "ecx" ], out => [ "none" ] },
671         ins       => [ "base", "index", "mem", "count" ],
672         emit      => '. shr%M %SB3, %AM',
673         units     => [ "GP" ],
674         mode      => "mode_M",
675         latency   => 1,
676         modified_flags => $status_flags
677 },
678
679 ShrD => {
680         irn_flags => [ "rematerializable" ],
681         reg_req   => { in => [ "gp", "gp", "ecx" ],
682                        out => [ "in_r1 !in_r2 !in_r3", "flags" ] },
683         ins       => [ "val_high", "val_low", "count" ],
684         outs      => [ "res", "flags" ],
685         emit      => ". shrd%M %SB2, %S1, %D0",
686         latency   => 6,
687         units     => [ "GP" ],
688         mode      => $mode_gp,
689         modified_flags => $status_flags
690 },
691
692 Sar => {
693         irn_flags => [ "rematerializable" ],
694         reg_req   => { in => [ "gp", "ecx" ],
695                        out => [ "in_r1 !in_r2", "flags" ] },
696         ins       => [ "val", "count" ],
697         outs      => [ "res", "flags" ],
698         emit      => '. sar%M %SB1, %S0',
699         units     => [ "GP" ],
700         latency   => 1,
701         mode      => $mode_gp,
702         modified_flags => $status_flags
703 },
704
705 SarMem => {
706         irn_flags => [ "rematerializable" ],
707         state     => "exc_pinned",
708         reg_req   => { in => [ "gp", "gp", "none", "ecx" ], out => [ "none" ] },
709         ins       => [ "base", "index", "mem", "count" ],
710         emit      => '. sar%M %SB3, %AM',
711         units     => [ "GP" ],
712         latency   => 1,
713         mode      => "mode_M",
714         modified_flags => $status_flags
715 },
716
717 Ror => {
718         irn_flags => [ "rematerializable" ],
719         reg_req   => { in => [ "gp", "ecx" ],
720                        out => [ "in_r1 !in_r2", "flags" ] },
721         ins       => [ "val", "count" ],
722         outs      => [ "res", "flags" ],
723         emit      => '. ror%M %SB1, %S0',
724         units     => [ "GP" ],
725         latency   => 1,
726         mode      => $mode_gp,
727         modified_flags => $status_flags
728 },
729
730 RorMem => {
731         irn_flags => [ "rematerializable" ],
732         state     => "exc_pinned",
733         reg_req   => { in => [ "gp", "gp", "none", "ecx" ], out => [ "none" ] },
734         ins       => [ "base", "index", "mem", "count" ],
735         emit      => '. ror%M %SB3, %AM',
736         units     => [ "GP" ],
737         latency   => 1,
738         mode      => "mode_M",
739         modified_flags => $status_flags
740 },
741
742 Rol => {
743         irn_flags => [ "rematerializable" ],
744         reg_req   => { in => [ "gp", "ecx" ],
745                        out => [ "in_r1 !in_r2", "flags" ] },
746         ins       => [ "val", "count" ],
747         outs      => [ "res", "flags" ],
748         emit      => '. rol%M %SB1, %S0',
749         units     => [ "GP" ],
750         latency   => 1,
751         mode      => $mode_gp,
752         modified_flags => $status_flags
753 },
754
755 RolMem => {
756         irn_flags => [ "rematerializable" ],
757         state     => "exc_pinned",
758         reg_req   => { in => [ "gp", "gp", "none", "ecx" ], out => [ "none" ] },
759         ins       => [ "base", "index", "mem", "count" ],
760         emit      => '. rol%M %SB3, %AM',
761         units     => [ "GP" ],
762         latency   => 1,
763         mode      => "mode_M",
764         modified_flags => $status_flags
765 },
766
767 Neg => {
768         irn_flags => [ "rematerializable" ],
769         reg_req   => { in => [ "gp" ],
770                        out => [ "in_r1", "flags" ] },
771         emit      => '. neg%M %S0',
772         ins       => [ "val" ],
773         outs      => [ "res", "flags" ],
774         units     => [ "GP" ],
775         latency   => 1,
776         mode      => $mode_gp,
777         modified_flags => $status_flags
778 },
779
780 NegMem => {
781         irn_flags => [ "rematerializable" ],
782         state     => "exc_pinned",
783         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "none" ] },
784         ins       => [ "base", "index", "mem" ],
785         emit      => '. neg%M %AM',
786         units     => [ "GP" ],
787         latency   => 1,
788         mode      => "mode_M",
789         modified_flags => $status_flags
790 },
791
792 Minus64Bit => {
793         irn_flags => [ "rematerializable" ],
794         reg_req   => { in => [ "gp", "gp" ], out => [ "in_r1", "in_r2" ] },
795         outs      => [ "low_res", "high_res" ],
796         units     => [ "GP" ],
797         latency   => 3,
798         modified_flags => $status_flags
799 },
800
801
802 Inc => {
803         irn_flags => [ "rematerializable" ],
804         reg_req   => { in => [ "gp" ],
805                        out => [ "in_r1", "flags" ] },
806         ins       => [ "val" ],
807         outs      => [ "res", "flags" ],
808         emit      => '. inc%M %S0',
809         units     => [ "GP" ],
810         mode      => $mode_gp,
811         latency   => 1,
812         modified_flags => $status_flags_wo_cf
813 },
814
815 IncMem => {
816         irn_flags => [ "rematerializable" ],
817         state     => "exc_pinned",
818         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "none" ] },
819         ins       => [ "base", "index", "mem" ],
820         emit      => '. inc%M %AM',
821         units     => [ "GP" ],
822         mode      => "mode_M",
823         latency   => 1,
824         modified_flags => $status_flags_wo_cf
825 },
826
827 Dec => {
828         irn_flags => [ "rematerializable" ],
829         reg_req   => { in => [ "gp" ],
830                        out => [ "in_r1", "flags" ] },
831         ins       => [ "val" ],
832         outs      => [ "res", "flags" ],
833         emit      => '. dec%M %S0',
834         units     => [ "GP" ],
835         mode      => $mode_gp,
836         latency   => 1,
837         modified_flags => $status_flags_wo_cf
838 },
839
840 DecMem => {
841         irn_flags => [ "rematerializable" ],
842         state     => "exc_pinned",
843         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "none" ] },
844         ins       => [ "base", "index", "mem" ],
845         emit      => '. dec%M %AM',
846         units     => [ "GP" ],
847         mode      => "mode_M",
848         latency   => 1,
849         modified_flags => $status_flags_wo_cf
850 },
851
852 Not => {
853         irn_flags => [ "rematerializable" ],
854         reg_req   => { in => [ "gp" ],
855                        out => [ "in_r1" ] },
856         ins       => [ "val" ],
857         outs      => [ "res" ],
858         emit      => '. not%M %S0',
859         units     => [ "GP" ],
860         latency   => 1,
861         mode      => $mode_gp,
862         # no flags modified
863 },
864
865 NotMem => {
866         irn_flags => [ "rematerializable" ],
867         state     => "exc_pinned",
868         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "none" ] },
869         ins       => [ "base", "index", "mem" ],
870         emit      => '. not%M %AM',
871         units     => [ "GP" ],
872         latency   => 1,
873         mode      => "mode_M",
874         # no flags modified
875 },
876
877 Cmc => {
878         reg_req   => { in => [ "flags" ], out => [ "flags" ] },
879         emit      => '.cmc',
880         units     => [ "GP" ],
881         latency   => 1,
882         mode      => $mode_flags,
883         modified_flags => $status_flags
884 },
885
886 Stc => {
887         reg_req   => { out => [ "flags" ] },
888         emit      => '.stc',
889         units     => [ "GP" ],
890         latency   => 1,
891         mode      => $mode_flags,
892         modified_flags => $status_flags
893 },
894
895 Cmp => {
896         irn_flags => [ "rematerializable" ],
897         state     => "exc_pinned",
898         reg_req   => { in  => [ "gp", "gp", "none", "gp", "gp" ],
899                        out => [ "flags", "none", "none" ] },
900         ins       => [ "base", "index", "mem", "left", "right" ],
901         outs      => [ "eflags", "unused", "M" ],
902         am        => "source,binary",
903         emit      => '. cmp%M %binop',
904         attr      => "bool ins_permuted",
905         init_attr => "attr->data.ins_permuted   = ins_permuted;",
906         latency   => 1,
907         units     => [ "GP" ],
908         mode      => $mode_flags,
909         modified_flags => $status_flags
910 },
911
912 Cmp8Bit => {
913         irn_flags => [ "rematerializable" ],
914         state     => "exc_pinned",
915         reg_req   => { in => [ "gp", "gp", "none", "eax ebx ecx edx", "eax ebx ecx edx" ] ,
916                        out => [ "flags", "none", "none" ] },
917         ins       => [ "base", "index", "mem", "left", "right" ],
918         outs      => [ "eflags", "unused", "M" ],
919         am        => "source,binary",
920         emit      => '. cmpb %binop',
921         attr      => "bool ins_permuted",
922         init_attr => "attr->data.ins_permuted   = ins_permuted;",
923         latency   => 1,
924         units     => [ "GP" ],
925         mode      => $mode_flags,
926         modified_flags => $status_flags
927 },
928
929 XorHighLow => {
930         irn_flags => [ "rematerializable" ],
931         state     => "exc_pinned",
932         reg_req   => { in => [ "eax ebx ecx edx" ],
933                        out => [ "in_r1", "flags" ] },
934         emit      => '. xorb %SH0, %SB0',
935         ins       => [ "value" ],
936         outs      => [ "res", "flags" ],
937         units     => [ "GP" ],
938         latency   => 1,
939         mode      => $mode_gp,
940         modified_flags => $status_flags,
941 },
942
943 Test => {
944         irn_flags => [ "rematerializable" ],
945         state     => "exc_pinned",
946         reg_req   => { in => [ "gp", "gp", "none", "gp", "gp" ] ,
947                        out => [ "flags", "none", "none" ] },
948         ins       => [ "base", "index", "mem", "left", "right" ],
949         outs      => [ "eflags", "unused", "M" ],
950         am        => "source,binary",
951         emit      => '. test%M %binop',
952         attr      => "bool ins_permuted",
953         init_attr => "attr->data.ins_permuted = ins_permuted;",
954         latency   => 1,
955         units     => [ "GP" ],
956         mode      => $mode_flags,
957         modified_flags => $status_flags
958 },
959
960 Test8Bit => {
961         irn_flags => [ "rematerializable" ],
962         state     => "exc_pinned",
963         reg_req   => { in => [ "gp", "gp", "none", "eax ebx ecx edx", "eax ebx ecx edx" ] ,
964                        out => [ "flags", "none", "none" ] },
965         ins       => [ "base", "index", "mem", "left", "right" ],
966         outs      => [ "eflags", "unused", "M" ],
967         am        => "source,binary",
968         emit      => '. testb %binop',
969         attr      => "bool ins_permuted",
970         init_attr => "attr->data.ins_permuted = ins_permuted;",
971         latency   => 1,
972         units     => [ "GP" ],
973         mode      => $mode_flags,
974         modified_flags => $status_flags
975 },
976
977 Setcc => {
978         #irn_flags => [ "rematerializable" ],
979         reg_req   => { in => [ "eflags" ], out => [ "eax ebx ecx edx" ] },
980         ins       => [ "eflags" ],
981         outs      => [ "res" ],
982         attr_type => "ia32_condcode_attr_t",
983         attr      => "ia32_condition_code_t condition_code",
984         # The way we handle Setcc with float nodes (potentially) destroys the flags
985         # (when we emit the setX; setp; orb and the setX;setnp;andb sequences)
986         init_attr => "set_ia32_ls_mode(res, mode_Bu);\n"
987                 . "\tif (condition_code & ia32_cc_additional_float_cases) {\n"
988                 . "\t\tarch_add_irn_flags(res, arch_irn_flags_modify_flags);\n"
989                 . "\t\t/* attr->latency = 3; */\n"
990                 . "\t}\n",
991         latency   => 1,
992         units     => [ "GP" ],
993         mode      => $mode_gp,
994 },
995
996 SetccMem => {
997         #irn_flags => [ "rematerializable" ],
998         state     => "exc_pinned",
999         reg_req   => { in => [ "gp", "gp", "none", "eflags" ], out => [ "none" ] },
1000         ins       => [ "base", "index", "mem","eflags" ],
1001         attr_type => "ia32_condcode_attr_t",
1002         attr      => "ia32_condition_code_t condition_code",
1003         init_attr => "set_ia32_ls_mode(res, mode_Bu);\n",
1004         emit      => '. set%CMP3 %AM',
1005         latency   => 1,
1006         units     => [ "GP" ],
1007         mode      => 'mode_M',
1008 },
1009
1010 CMovcc => {
1011         #irn_flags => [ "rematerializable" ],
1012         state     => "exc_pinned",
1013         # (note: leave the false,true order intact to make it compatible with other
1014         #  ia32_binary ops)
1015         reg_req   => { in => [ "gp", "gp", "none", "gp", "gp", "eflags" ],
1016                        out => [ "in_r4 in_r5", "flags", "none" ] },
1017         ins       => [ "base", "index", "mem", "val_false", "val_true", "eflags" ],
1018         outs      => [ "res", "flags", "M" ],
1019         am        => "source,binary",
1020         attr_type => "ia32_condcode_attr_t",
1021         attr      => "ia32_condition_code_t condition_code",
1022         latency   => 1,
1023         units     => [ "GP" ],
1024         mode      => $mode_gp,
1025 },
1026
1027 Jcc => {
1028         state     => "pinned",
1029         op_flags  => [ "labeled", "cfopcode", "forking" ],
1030         reg_req   => { in  => [ "eflags" ], out => [ "none", "none" ] },
1031         ins       => [ "eflags" ],
1032         outs      => [ "false", "true" ],
1033         attr_type => "ia32_condcode_attr_t",
1034         attr      => "ia32_condition_code_t condition_code",
1035         latency   => 2,
1036         units     => [ "BRANCH" ],
1037 },
1038
1039 SwitchJmp => {
1040         state     => "pinned",
1041         op_flags  => [ "labeled", "cfopcode", "forking" ],
1042         reg_req   => { in => [ "gp", "gp" ] },
1043         ins       => [ "base", "index" ],
1044         mode      => "mode_T",
1045         attr_type => "ia32_switch_attr_t",
1046         attr      => "long default_pn",
1047         latency   => 2,
1048         units     => [ "BRANCH" ],
1049         init_attr => "info->out_infos = NULL;", # XXX ugly hack for out requirements
1050 },
1051
1052 Jmp => {
1053         state     => "pinned",
1054         irn_flags => [ "simple_jump" ],
1055         op_flags  => [ "cfopcode" ],
1056         reg_req   => { out => [ "none" ] },
1057         latency   => 1,
1058         units     => [ "BRANCH" ],
1059         mode      => "mode_X",
1060 },
1061
1062 IJmp => {
1063         state     => "pinned",
1064         op_flags  => [ "cfopcode", "unknown_jump" ],
1065         reg_req   => { in => [ "gp", "gp", "none", "gp" ] },
1066         ins       => [ "base", "index", "mem", "target" ],
1067         am        => "source,unary",
1068         emit      => '. jmp *%unop3',
1069         latency   => 1,
1070         units     => [ "BRANCH" ],
1071         mode      => "mode_X",
1072         init_attr => "info->out_infos = NULL;", # XXX ugly hack for out requirements
1073 },
1074
1075 Const => {
1076         op_flags  => [ "constlike" ],
1077         irn_flags => [ "rematerializable" ],
1078         reg_req   => { out => [ "gp" ] },
1079         units     => [ "GP" ],
1080         attr      => "ir_entity *symconst, int symconst_sign, int no_pic_adjust, long offset",
1081         attr_type => "ia32_immediate_attr_t",
1082         latency   => 1,
1083         mode      => $mode_gp,
1084 },
1085
1086 Unknown => {
1087         op_flags  => [ "constlike" ],
1088         irn_flags => [ "rematerializable" ],
1089         reg_req   => { out => [ "gp" ] },
1090         latency   => 0,
1091         emit      => '',
1092         mode      => $mode_gp,
1093 },
1094
1095 GetEIP => {
1096         op_flags => [ "constlike" ],
1097         reg_req  => { out => [ "gp" ] },
1098         units    => [ "GP" ],
1099         latency  => 5,
1100         mode     => $mode_gp,
1101         modified_flags => $status_flags,
1102 },
1103
1104 NoReg_GP => {
1105         state     => "pinned",
1106         op_flags  => [ "constlike", "dump_noblock", "dump_noinput" ],
1107         irn_flags => [ "not_scheduled" ],
1108         reg_req   => { out => [ "gp_NOREG:I" ] },
1109         units     => [],
1110         emit      => "",
1111         latency   => 0,
1112         mode      => $mode_gp
1113 },
1114
1115 NoReg_VFP => {
1116         state     => "pinned",
1117         op_flags  => [ "constlike", "dump_noblock", "dump_noinput" ],
1118         irn_flags => [ "not_scheduled" ],
1119         reg_req   => { out => [ "vfp_NOREG:I" ] },
1120         units     => [],
1121         emit      => "",
1122         mode      => "mode_E",
1123         latency   => 0,
1124         attr_type => "ia32_x87_attr_t",
1125 },
1126
1127 NoReg_XMM => {
1128         state     => "pinned",
1129         op_flags  => [ "constlike", "dump_noblock", "dump_noinput" ],
1130         irn_flags => [ "not_scheduled" ],
1131         reg_req   => { out => [ "xmm_NOREG:I" ] },
1132         units     => [],
1133         emit      => "",
1134         latency   => 0,
1135         mode      => "mode_E"
1136 },
1137
1138 ChangeCW => {
1139         state     => "pinned",
1140         op_flags  => [ "constlike" ],
1141         irn_flags => [ "not_scheduled" ],
1142         reg_req   => { out => [ "fpcw:I" ] },
1143         mode      => $mode_fpcw,
1144         latency   => 3,
1145         units     => [ "GP" ],
1146         modified_flags => $fpcw_flags
1147 },
1148
1149 FldCW => {
1150         op_flags  => [ "labeled" ],
1151         state     => "pinned",
1152         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "fpcw:I" ] },
1153         ins       => [ "base", "index", "mem" ],
1154         latency   => 5,
1155         emit      => ". fldcw %AM",
1156         mode      => $mode_fpcw,
1157         units     => [ "GP" ],
1158         modified_flags => $fpcw_flags
1159 },
1160
1161 FnstCW => {
1162         op_flags  => [ "labeled" ],
1163         state     => "pinned",
1164         reg_req   => { in => [ "gp", "gp", "none", "fp_cw" ], out => [ "none" ] },
1165         ins       => [ "base", "index", "mem", "fpcw" ],
1166         latency   => 5,
1167         emit      => ". fnstcw %AM",
1168         mode      => "mode_M",
1169         units     => [ "GP" ],
1170 },
1171
1172 FnstCWNOP => {
1173         op_flags  => [ "labeled" ],
1174         state     => "pinned",
1175         reg_req   => { in => [ "fp_cw" ], out => [ "none" ] },
1176         ins       => [ "fpcw" ],
1177         latency   => 0,
1178         emit      => "",
1179         mode      => "mode_M",
1180 },
1181
1182 Cltd => {
1183         # we should not rematrialize this node. It has very strict constraints.
1184         reg_req   => { in => [ "eax", "edx" ], out => [ "edx" ] },
1185         ins       => [ "val", "clobbered" ],
1186         emit      => '. cltd',
1187         latency   => 1,
1188         mode      => $mode_gp,
1189         units     => [ "GP" ],
1190 },
1191
1192 # Load / Store
1193 #
1194 # Note that we add additional latency values depending on address mode, so a
1195 # lateny of 0 for load is correct
1196
1197 Load => {
1198         op_flags  => [ "fragile", "labeled" ],
1199         state     => "exc_pinned",
1200         reg_req   => { in => [ "gp", "gp", "none" ],
1201                        out => [ "gp", "none", "none", "none", "none" ] },
1202         ins       => [ "base", "index", "mem" ],
1203         outs      => [ "res", "unused", "M", "X_regular", "X_except" ],
1204         latency   => 0,
1205         emit      => ". mov%EX%.l %AM, %D0",
1206         units     => [ "GP" ],
1207 },
1208
1209 Store => {
1210         op_flags  => [ "fragile", "labeled" ],
1211         state     => "exc_pinned",
1212         reg_req   => { in => [ "gp", "gp", "none", "gp" ],
1213                        out => [ "none", "none", "none" ] },
1214         ins       => [ "base", "index", "mem", "val" ],
1215         outs      => [ "M", "X_regular", "X_except" ],
1216         emit      => '. mov%M %SI3, %AM',
1217         latency   => 2,
1218         units     => [ "GP" ],
1219 },
1220
1221 Store8Bit => {
1222         op_flags  => [ "fragile", "labeled" ],
1223         state     => "exc_pinned",
1224         reg_req   => { in => [ "gp", "gp", "none", "eax ebx ecx edx" ],
1225                        out => ["none", "none", "none" ] },
1226         ins       => [ "base", "index", "mem", "val" ],
1227         outs      => [ "M", "X_regular", "X_except" ],
1228         emit      => '. mov%M %SB3, %AM',
1229         latency   => 2,
1230         units     => [ "GP" ],
1231 },
1232
1233 Lea => {
1234         irn_flags => [ "rematerializable" ],
1235         reg_req   => { in => [ "gp", "gp" ], out => [ "gp" ] },
1236         ins       => [ "base", "index" ],
1237         emit      => '. leal %AM, %D0',
1238         latency   => 2,
1239         units     => [ "GP" ],
1240         mode      => $mode_gp,
1241 # lea doesn't modify the flags, but setting this seems advantageous since it
1242 # increases chances that the Lea is transformed back to an Add
1243         modified_flags => 1,
1244 },
1245
1246 Push => {
1247         state     => "exc_pinned",
1248         reg_req   => { in => [ "gp", "gp", "none", "gp", "esp" ], out => [ "esp:I|S", "none" ] },
1249         ins       => [ "base", "index", "mem", "val", "stack" ],
1250         emit      => '. push%M %unop3',
1251         outs      => [ "stack", "M" ],
1252         am        => "source,unary",
1253         latency   => 2,
1254         units     => [ "GP" ],
1255 },
1256
1257 PushEax => {
1258         state   => "exc_pinned",
1259         reg_req => { in => [ "esp" ], out => [ "esp:I|S" ] },
1260         ins     => [ "stack" ],
1261         outs    => [ "stack" ],
1262         emit    => '. pushl %%eax',
1263         latency => 2,
1264         units   => [ "GP" ],
1265         mode    => $mode_gp,
1266 },
1267
1268 Pop => {
1269         state     => "exc_pinned",
1270         reg_req   => { in => [ "none", "esp" ], out => [ "gp", "none", "none", "esp:I|S" ] },
1271         ins       => [ "mem", "stack" ],
1272         outs      => [ "res", "M", "unused", "stack" ],
1273         emit      => '. pop%M %D0',
1274         latency   => 3, # Pop is more expensive than Push on Athlon
1275         units     => [ "GP" ],
1276 },
1277
1278 PopEbp => {
1279         state     => "exc_pinned",
1280         reg_req   => { in => [ "none", "esp" ], out => [ "ebp:I", "none", "none", "esp:I|S" ] },
1281         ins       => [ "mem", "stack" ],
1282         outs      => [ "res", "M", "unused", "stack" ],
1283         emit      => '. pop%M %D0',
1284         latency   => 3, # Pop is more expensive than Push on Athlon
1285         units     => [ "GP" ],
1286 },
1287
1288 CopyEbpEsp => {
1289         state     => "exc_pinned",
1290         reg_req   => { in => [ "ebp" ], out => [ "esp:I|S" ] },
1291         ins       => [ "ebp" ],
1292         outs      => [ "esp" ],
1293         emit      => '. movl %S0, %D0',
1294         latency   => 1,
1295         units     => [ "GP" ],
1296         mode      => $mode_gp,
1297 },
1298
1299 PopMem => {
1300         state     => "exc_pinned",
1301         reg_req   => { in => [ "gp", "gp", "none", "esp" ], out => [ "none", "none", "none", "esp:I|S" ] },
1302         ins       => [ "base", "index", "mem", "stack" ],
1303         outs      => [ "unused0", "M", "unused1", "stack" ],
1304         emit      => '. pop%M %AM',
1305         latency   => 3, # Pop is more expensive than Push on Athlon
1306         units     => [ "GP" ],
1307 },
1308
1309 Enter => {
1310         reg_req   => { in => [ "esp" ], out => [ "ebp", "esp:I|S", "none" ] },
1311         emit      => '. enter',
1312         outs      => [ "frame", "stack", "M" ],
1313         latency   => 15,
1314         units     => [ "GP" ],
1315 },
1316
1317 Leave => {
1318         reg_req   => { in => [ "ebp" ], out => [ "ebp:I", "esp:I|S" ] },
1319         emit      => '. leave',
1320         outs      => [ "frame", "stack" ],
1321         latency   => 3,
1322         units     => [ "GP" ],
1323         state     => "exc_pinned",
1324 },
1325
1326 AddSP => {
1327         state     => "pinned",
1328         reg_req   => { in => [ "gp", "gp", "none", "esp", "gp" ], out => [ "esp:I|S", "none" ] },
1329         ins       => [ "base", "index", "mem", "stack", "size" ],
1330         am        => "source,binary",
1331         emit      => '. addl %binop',
1332         latency   => 1,
1333         outs      => [ "stack", "M" ],
1334         units     => [ "GP" ],
1335         modified_flags => $status_flags
1336 },
1337
1338 SubSP => {
1339         state     => "pinned",
1340         reg_req   => { in => [ "gp", "gp", "none", "esp", "gp" ], out => [ "esp:I|S", "gp", "none" ] },
1341         ins       => [ "base", "index", "mem", "stack", "size" ],
1342         am        => "source,binary",
1343         emit      => ". subl %binop\n".
1344                      ". movl %%esp, %D1",
1345         latency   => 2,
1346         outs      => [ "stack", "addr", "M" ],
1347         units     => [ "GP" ],
1348         modified_flags => $status_flags
1349 },
1350
1351 RepPrefix => {
1352         op_flags  => [ "keep" ],
1353         state     => "pinned",
1354         mode      => "mode_M",
1355         emit      => ". rep",
1356         latency   => 0,
1357 },
1358
1359 LdTls => {
1360         irn_flags => [ "rematerializable" ],
1361         reg_req   => { out => [ "gp" ] },
1362         units     => [ "GP" ],
1363         emit      => ". movl %%gs:0, %D0",
1364         mode      => $mode_gp,
1365         latency   => 1,
1366 },
1367
1368 #
1369 # BT supports source address mode, but this is unused yet
1370 #
1371 Bt => {
1372         irn_flags => [ "rematerializable" ],
1373         state     => "exc_pinned",
1374         reg_req   => { in => [ "gp", "gp" ], out => [ "flags" ] },
1375         ins       => [ "left", "right" ],
1376         emit      => '. bt%M %S1, %S0',
1377         units     => [ "GP" ],
1378         latency   => 1,
1379         mode      => $mode_flags,
1380         modified_flags => $status_flags  # only CF is set, but the other flags are undefined
1381 },
1382
1383 Bsf => {
1384         irn_flags => [ "rematerializable" ],
1385         state     => "exc_pinned",
1386         reg_req   => { in => [ "gp", "gp", "none", "gp" ],
1387                        out => [ "gp", "flags", "none" ] },
1388         ins       => [ "base", "index", "mem", "operand" ],
1389         outs      => [ "res", "flags", "M" ],
1390         am        => "source,binary",
1391         emit      => '. bsf%M %unop3, %D0',
1392         units     => [ "GP" ],
1393         latency   => 1,
1394         mode      => $mode_gp,
1395         modified_flags => $status_flags
1396 },
1397
1398 Bsr => {
1399         irn_flags => [ "rematerializable" ],
1400         state     => "exc_pinned",
1401         reg_req   => { in => [ "gp", "gp", "none", "gp" ],
1402                        out => [ "gp", "flags", "none" ] },
1403         ins       => [ "base", "index", "mem", "operand" ],
1404         outs      => [ "res", "flags", "M" ],
1405         am        => "source,binary",
1406         emit      => '. bsr%M %unop3, %D0',
1407         units     => [ "GP" ],
1408         latency   => 1,
1409         mode      => $mode_gp,
1410         modified_flags => $status_flags
1411 },
1412
1413 #
1414 # SSE4.2 or SSE4a popcnt instruction
1415 #
1416 Popcnt => {
1417         irn_flags => [ "rematerializable" ],
1418         state     => "exc_pinned",
1419         reg_req   => { in => [ "gp", "gp", "none", "gp" ],
1420                        out => [ "gp", "flags", "none" ] },
1421         ins       => [ "base", "index", "mem", "operand" ],
1422         outs      => [ "res", "flags", "M" ],
1423         am        => "source,binary",
1424         emit      => '. popcnt%M %unop3, %D0',
1425         units     => [ "GP" ],
1426         latency   => 1,
1427         mode      => $mode_gp,
1428         modified_flags => $status_flags
1429 },
1430
1431 Call => {
1432         op_flags  => [ "fragile" ],
1433         state     => "exc_pinned",
1434         reg_req   => {
1435                 in  => [ "gp", "gp", "none", "gp", "esp", "fpcw", "eax", "ecx", "edx" ],
1436                 out => [ "esp:I|S", "fpcw:I", "none", "eax", "ecx", "edx", "vf0", "vf1", "vf2", "vf3", "vf4", "vf5", "vf6", "vf7", "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7", "none", "none" ]
1437         },
1438         ins       => [ "base", "index", "mem", "addr", "stack", "fpcw", "eax", "ecx", "edx" ],
1439         outs      => [ "stack", "fpcw", "M", "eax", "ecx", "edx", "vf0", "vf1", "vf2", "vf3", "vf4", "vf5", "vf6", "vf7", "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7", "X_regular", "X_except" ],
1440         attr_type => "ia32_call_attr_t",
1441         attr      => "unsigned pop, ir_type *call_tp",
1442         am        => "source,unary",
1443         units     => [ "BRANCH" ],
1444         latency   => 4, # random number
1445         modified_flags => $status_flags
1446 },
1447
1448 #
1449 # a Helper node for frame-climbing, needed for __builtin_(frame|return)_address
1450 #
1451 # PS: try gcc __builtin_frame_address(100000) :-)
1452 #
1453 ClimbFrame => {
1454         reg_req   => { in => [ "gp", "gp", "gp"], out => [ "in_r3" ] },
1455         ins       => [ "frame", "cnt", "tmp" ],
1456         outs      => [ "res" ],
1457         latency   => 4, # random number
1458         attr_type => "ia32_climbframe_attr_t",
1459         attr      => "unsigned count",
1460         units     => [ "GP" ],
1461         mode      => $mode_gp
1462 },
1463
1464 #
1465 # bswap
1466 #
1467 Bswap => {
1468         irn_flags => [ "rematerializable" ],
1469         reg_req   => { in => [ "gp" ],
1470                        out => [ "in_r1" ] },
1471         emit      => '. bswap%M %S0',
1472         ins       => [ "val" ],
1473         units     => [ "GP" ],
1474         latency   => 1,
1475         mode      => $mode_gp,
1476 },
1477
1478 #
1479 # bswap16, use xchg here
1480 #
1481 Bswap16 => {
1482         irn_flags => [ "rematerializable" ],
1483         reg_req   => { in => [ "eax ebx ecx edx" ],
1484                        out => [ "in_r1" ] },
1485         emit      => '. xchg %SB0, %SH0',
1486         ins       => [ "val" ],
1487         units     => [ "GP" ],
1488         latency   => 1,
1489         mode      => $mode_gp,
1490 },
1491
1492 #
1493 # BreakPoint
1494 #
1495 Breakpoint => {
1496         state     => "pinned",
1497         reg_req   => { in => [ "none" ], out => [ "none" ] },
1498         ins       => [ "mem" ],
1499         latency   => 0,
1500         emit      => ". int3",
1501         units     => [ "GP" ],
1502         mode      => mode_M,
1503 },
1504
1505 #
1506 # Undefined Instruction on ALL x86 CPU's
1507 #
1508 UD2 => {
1509         state     => "pinned",
1510         reg_req   => { in => [ "none" ], out => [ "none" ] },
1511         ins       => [ "mem" ],
1512         latency   => 0,
1513         emit      => ". .value  0x0b0f",
1514         units     => [ "GP" ],
1515         mode      => mode_M,
1516 },
1517
1518 #
1519 # outport
1520 #
1521 Outport => {
1522         irn_flags => [ "rematerializable" ],
1523         state     => "pinned",
1524         reg_req   => { in => [ "edx", "eax", "none" ], out => [ "none" ] },
1525         ins       => [ "port", "value", "mem" ],
1526         emit      => '. out%M %SS0, %SI1',
1527         units     => [ "GP" ],
1528         latency   => 1,
1529         mode      => mode_M,
1530         modified_flags => $status_flags
1531 },
1532
1533 #
1534 # inport
1535 #
1536 Inport => {
1537         irn_flags => [ "rematerializable" ],
1538         state     => "pinned",
1539         reg_req   => { in => [ "edx", "none" ], out => [ "eax", "none" ] },
1540         ins       => [ "port", "mem" ],
1541         outs      => [ "res", "M" ],
1542         emit      => '. in%M %DS0, %SS0',
1543         units     => [ "GP" ],
1544         latency   => 1,
1545         mode      => mode_T,
1546         modified_flags => $status_flags
1547 },
1548
1549 #
1550 # Intel style prefetching
1551 #
1552 Prefetch0 => {
1553         op_flags  => [ "labeled" ],
1554         state     => "exc_pinned",
1555         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "none" ] },
1556         ins       => [ "base", "index", "mem" ],
1557         outs      => [ "M" ],
1558         latency   => 0,
1559         emit      => ". prefetcht0 %AM",
1560         units     => [ "GP" ],
1561 },
1562
1563 Prefetch1 => {
1564         op_flags  => [ "labeled" ],
1565         state     => "exc_pinned",
1566         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "none" ] },
1567         ins       => [ "base", "index", "mem" ],
1568         outs      => [ "M" ],
1569         latency   => 0,
1570         emit      => ". prefetcht1 %AM",
1571         units     => [ "GP" ],
1572 },
1573
1574 Prefetch2 => {
1575         op_flags  => [ "labeled" ],
1576         state     => "exc_pinned",
1577         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "none" ] },
1578         ins       => [ "base", "index", "mem" ],
1579         outs      => [ "M" ],
1580         latency   => 0,
1581         emit      => ". prefetcht2 %AM",
1582         units     => [ "GP" ],
1583 },
1584
1585 PrefetchNTA => {
1586         op_flags  => [ "labeled" ],
1587         state     => "exc_pinned",
1588         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "none" ] },
1589         ins       => [ "base", "index", "mem" ],
1590         outs      => [ "M" ],
1591         latency   => 0,
1592         emit      => ". prefetchnta %AM",
1593         units     => [ "GP" ],
1594 },
1595
1596 #
1597 # 3DNow! prefetch instructions
1598 #
1599 Prefetch => {
1600         op_flags  => [ "labeled" ],
1601         state     => "exc_pinned",
1602         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "none" ] },
1603         ins       => [ "base", "index", "mem" ],
1604         outs      => [ "M" ],
1605         latency   => 0,
1606         emit      => ". prefetch %AM",
1607         units     => [ "GP" ],
1608 },
1609
1610 PrefetchW => {
1611         op_flags  => [ "labeled" ],
1612         state     => "exc_pinned",
1613         reg_req   => { in => [ "gp", "gp", "none" ], out => [ "none" ] },
1614         ins       => [ "base", "index", "mem" ],
1615         outs      => [ "M" ],
1616         latency   => 0,
1617         emit      => ". prefetchw %AM",
1618         units     => [ "GP" ],
1619 },
1620
1621 # produces a 0/+0.0
1622 xZero => {
1623         irn_flags => [ "rematerializable" ],
1624         reg_req   => { out => [ "xmm" ] },
1625         emit      => '. xorp%XSD %D0, %D0',
1626         latency   => 3,
1627         units     => [ "SSE" ],
1628         mode      => $mode_xmm
1629 },
1630
1631 xUnknown => {
1632         op_flags  => [ "constlike" ],
1633         irn_flags => [ "rematerializable" ],
1634         reg_req   => { out => [ "xmm" ] },
1635         emit      => '',
1636         latency   => 0,
1637         mode      => $mode_xmm
1638 },
1639
1640 xPzero => {
1641         irn_flags => [ "rematerializable" ],
1642         reg_req   => { out => [ "xmm" ] },
1643         emit      => '. pxor %D0, %D0',
1644         latency   => 3,
1645         units     => [ "SSE" ],
1646         mode      => $mode_xmm
1647 },
1648
1649 # produces all 1 bits
1650 xAllOnes => {
1651         irn_flags => [ "rematerializable" ],
1652         reg_req   => { out => [ "xmm" ] },
1653         emit      => '. pcmpeqb %D0, %D0',
1654         latency   => 3,
1655         units     => [ "SSE" ],
1656         mode      => $mode_xmm
1657 },
1658
1659 # integer shift left, dword
1660 xPslld => {
1661         irn_flags => [ "rematerializable" ],
1662         reg_req   => { in => [ "xmm", "xmm" ], out => [ "in_r1 !in_r2" ] },
1663         emit      => '. pslld %SI1, %D0',
1664         latency   => 3,
1665         units     => [ "SSE" ],
1666         mode      => $mode_xmm
1667 },
1668
1669 # integer shift left, qword
1670 xPsllq => {
1671         irn_flags => [ "rematerializable" ],
1672         reg_req   => { in => [ "xmm", "xmm" ], out => [ "in_r1 !in_r2" ] },
1673         emit      => '. psllq %SI1, %D0',
1674         latency   => 3,
1675         units     => [ "SSE" ],
1676         mode      => $mode_xmm
1677 },
1678
1679 # integer shift right, dword
1680 xPsrld => {
1681         irn_flags => [ "rematerializable" ],
1682         reg_req   => { in => [ "xmm", "xmm" ], out => [ "in_r1 !in_r2" ] },
1683         emit      => '. psrld %SI1, %D0',
1684         latency   => 1,
1685         units     => [ "SSE" ],
1686         mode      => $mode_xmm
1687 },
1688
1689 # mov from integer to SSE register
1690 xMovd  => {
1691         irn_flags => [ "rematerializable" ],
1692         reg_req   => { in => [ "gp" ], out => [ "xmm" ] },
1693         emit      => '. movd %S0, %D0',
1694         latency   => 1,
1695         units     => [ "SSE" ],
1696         mode      => $mode_xmm
1697 },
1698
1699 xAdd => {
1700         irn_flags => [ "rematerializable" ],
1701         state     => "exc_pinned",
1702         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1703                        out => [ "in_r4 in_r5", "flags", "none" ] },
1704         ins       => [ "base", "index", "mem", "left", "right" ],
1705         outs      => [ "res", "flags", "M" ],
1706         am        => "source,binary",
1707         emit      => '. add%XXM %binop',
1708         latency   => 4,
1709         units     => [ "SSE" ],
1710         mode      => $mode_xmm
1711 },
1712
1713 xMul => {
1714         irn_flags => [ "rematerializable" ],
1715         state     => "exc_pinned",
1716         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1717                        out => [ "in_r4 in_r5", "flags", "none" ] },
1718         ins       => [ "base", "index", "mem", "left", "right" ],
1719         outs      => [ "res", "flags", "M" ],
1720         am        => "source,binary",
1721         emit      => '. mul%XXM %binop',
1722         latency   => 4,
1723         units     => [ "SSE" ],
1724         mode      => $mode_xmm
1725 },
1726
1727 xMax => {
1728         irn_flags => [ "rematerializable" ],
1729         state     => "exc_pinned",
1730         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1731                        out => [ "in_r4 in_r5", "flags", "none" ] },
1732         ins       => [ "base", "index", "mem", "left", "right" ],
1733         outs      => [ "res", "flags", "M" ],
1734         am        => "source,binary",
1735         emit      => '. max%XXM %binop',
1736         latency   => 2,
1737         units     => [ "SSE" ],
1738         mode      => $mode_xmm
1739 },
1740
1741 xMin => {
1742         irn_flags => [ "rematerializable" ],
1743         state     => "exc_pinned",
1744         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1745                        out => [ "in_r4 in_r5", "flags", "none" ] },
1746         ins       => [ "base", "index", "mem", "left", "right" ],
1747         outs      => [ "res", "flags", "M" ],
1748         am        => "source,binary",
1749         emit      => '. min%XXM %binop',
1750         latency   => 2,
1751         units     => [ "SSE" ],
1752         mode      => $mode_xmm
1753 },
1754
1755 xAnd => {
1756         irn_flags => [ "rematerializable" ],
1757         state     => "exc_pinned",
1758         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1759                        out => [ "in_r4 in_r5", "flags", "none" ] },
1760         ins       => [ "base", "index", "mem", "left", "right" ],
1761         outs      => [ "res", "flags", "M" ],
1762         am        => "source,binary",
1763         emit      => '. andp%XSD %binop',
1764         latency   => 3,
1765         units     => [ "SSE" ],
1766         mode      => $mode_xmm
1767 },
1768
1769 xOr => {
1770         irn_flags => [ "rematerializable" ],
1771         state     => "exc_pinned",
1772         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1773                        out => [ "in_r4 in_r5", "flags", "none" ] },
1774         ins       => [ "base", "index", "mem", "left", "right" ],
1775         outs      => [ "res", "flags", "M" ],
1776         am        => "source,binary",
1777         emit      => '. orp%XSD %binop',
1778         latency   => 3,
1779         units     => [ "SSE" ],
1780         mode      => $mode_xmm
1781 },
1782
1783 xXor => {
1784         irn_flags => [ "rematerializable" ],
1785         state     => "exc_pinned",
1786         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1787                        out => [ "in_r4 in_r5", "flags", "none" ] },
1788         ins       => [ "base", "index", "mem", "left", "right" ],
1789         outs      => [ "res", "flags", "M" ],
1790         am        => "source,binary",
1791         emit      => '. xorp%XSD %binop',
1792         latency   => 3,
1793         units     => [ "SSE" ],
1794         mode      => $mode_xmm
1795 },
1796
1797 xAndNot => {
1798         irn_flags => [ "rematerializable" ],
1799         state     => "exc_pinned",
1800         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1801                        out => [ "in_r4 !in_r5", "flags", "none" ] },
1802         ins       => [ "base", "index", "mem", "left", "right" ],
1803         outs      => [ "res", "flags", "M" ],
1804         am        => "source,binary",
1805         emit      => '. andnp%XSD %binop',
1806         latency   => 3,
1807         units     => [ "SSE" ],
1808         mode      => $mode_xmm
1809 },
1810
1811 xSub => {
1812         irn_flags => [ "rematerializable" ],
1813         state     => "exc_pinned",
1814         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1815                        out => [ "in_r4", "flags", "none" ] },
1816         ins       => [ "base", "index", "mem", "minuend", "subtrahend" ],
1817         outs      => [ "res", "flags", "M" ],
1818         am        => "source,binary",
1819         emit      => '. sub%XXM %binop',
1820         latency   => 4,
1821         units     => [ "SSE" ],
1822         mode      => $mode_xmm
1823 },
1824
1825 xDiv => {
1826         irn_flags => [ "rematerializable" ],
1827         state     => "exc_pinned",
1828         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1829                        out => [ "in_r4 !in_r5", "flags", "none" ] },
1830         ins       => [ "base", "index", "mem", "dividend", "divisor" ],
1831         outs      => [ "res", "flags", "M" ],
1832         am        => "source,binary",
1833         emit      => '. div%XXM %binop',
1834         latency   => 16,
1835         units     => [ "SSE" ],
1836 },
1837
1838 Ucomi => {
1839         irn_flags => [ "rematerializable" ],
1840         state     => "exc_pinned",
1841         reg_req   => { in => [ "gp", "gp", "none", "xmm", "xmm" ],
1842                        out => [ "eflags" ] },
1843         ins       => [ "base", "index", "mem", "left", "right" ],
1844         outs      => [ "flags" ],
1845         am        => "source,binary",
1846         attr      => "bool ins_permuted",
1847         init_attr => "attr->data.ins_permuted = ins_permuted;",
1848         emit      => ' .ucomi%XXM %binop',
1849         latency   => 3,
1850         units     => [ "SSE" ],
1851         mode      => $mode_flags,
1852         modified_flags => 1,
1853 },
1854
1855 xLoad => {
1856         op_flags  => [ "fragile", "labeled" ],
1857         state     => "exc_pinned",
1858         reg_req   => { in => [ "gp", "gp", "none" ],
1859                        out => [ "xmm", "none", "none", "none", "none" ] },
1860         ins       => [ "base", "index", "mem" ],
1861         outs      => [ "res", "unused", "M", "X_regular", "X_except" ],
1862         emit      => '. mov%XXM %AM, %D0',
1863         attr      => "ir_mode *load_mode",
1864         init_attr => "attr->ls_mode = load_mode;",
1865         latency   => 0,
1866         units     => [ "SSE" ],
1867 },
1868
1869 xStore => {
1870         op_flags => [ "fragile", "labeled" ],
1871         state    => "exc_pinned",
1872         reg_req  => { in => [ "gp", "gp", "none", "xmm" ],
1873                       out => [ "none", "none", "none" ] },
1874         ins       => [ "base", "index", "mem", "val" ],
1875         outs      => [ "M", "X_regular", "X_except" ],
1876         emit     => '. mov%XXM %S3, %AM',
1877         latency  => 0,
1878         units    => [ "SSE" ],
1879 },
1880
1881 xStoreSimple => {
1882         op_flags => [ "fragile", "labeled" ],
1883         state    => "exc_pinned",
1884         reg_req  => { in => [ "gp", "gp", "none", "xmm" ],
1885                       out => [ "none", "none", "none" ] },
1886         ins      => [ "base", "index", "mem", "val" ],
1887         outs     => [ "M", "X_regular", "X_except" ],
1888         emit     => '. mov%XXM %S3, %AM',
1889         latency  => 0,
1890         units    => [ "SSE" ],
1891 },
1892
1893 CvtSI2SS => {
1894         op_flags => [ "labeled" ],
1895         state     => "exc_pinned",
1896         reg_req  => { in => [ "gp", "gp", "none", "gp" ], out => [ "xmm" ] },
1897         ins      => [ "base", "index", "mem", "val" ],
1898         am       => "source,unary",
1899         emit     => '. cvtsi2ss %unop3, %D0',
1900         latency  => 2,
1901         units    => [ "SSE" ],
1902         mode     => $mode_xmm
1903 },
1904
1905 CvtSI2SD => {
1906         op_flags => [ "labeled" ],
1907         state     => "exc_pinned",
1908         reg_req  => { in => [ "gp", "gp", "none", "gp" ], out => [ "xmm" ] },
1909         ins      => [ "base", "index", "mem", "val" ],
1910         am       => "source,unary",
1911         emit     => '. cvtsi2sd %unop3, %D0',
1912         latency  => 2,
1913         units    => [ "SSE" ],
1914         mode     => $mode_xmm
1915 },
1916
1917
1918 l_LLtoFloat => {
1919         ins      => [ "val_high", "val_low" ],
1920         attr_type => "",
1921         dump_func => "NULL",
1922 },
1923
1924 l_FloattoLL => {
1925         ins      => [ "val" ],
1926         outs     => [ "res_high", "res_low" ],
1927         attr_type => "",
1928         dump_func => "NULL",
1929 },
1930
1931 CopyB => {
1932         op_flags  => [ "fragile" ],
1933         state     => "pinned",
1934         reg_req   => { in => [ "edi", "esi", "ecx", "none" ],
1935                        out => [ "edi", "esi", "ecx", "none", "none", "none" ] },
1936         ins       => [ "dest", "source", "count", "mem" ],
1937         outs      => [ "dest", "source", "count", "M", "X_regular", "X_except" ],
1938         attr_type => "ia32_copyb_attr_t",
1939         attr      => "unsigned size",
1940         units     => [ "GP" ],
1941         latency   => 3,
1942 # we don't care about this flag, so no need to mark this node
1943 #       modified_flags => [ "DF" ]
1944 },
1945
1946 CopyB_i => {
1947         op_flags  => [ "fragile" ],
1948         state     => "pinned",
1949         reg_req   => { in => [ "edi", "esi", "none" ],
1950                        out => [  "edi", "esi", "none", "none", "none" ] },
1951         ins       => [ "dest", "source", "mem" ],
1952         outs      => [ "dest", "source", "M", "X_regular", "X_except" ],
1953         attr_type => "ia32_copyb_attr_t",
1954         attr      => "unsigned size",
1955         units     => [ "GP" ],
1956         latency   => 3,
1957 # we don't care about this flag, so no need to mark this node
1958 #       modified_flags => [ "DF" ]
1959 },
1960
1961 Cwtl => {
1962         state     => "exc_pinned",
1963         reg_req   => { in => [ "eax" ], out => [ "eax" ] },
1964         ins       => [ "val" ],
1965         outs      => [ "res" ],
1966         emit      => '. cwtl',
1967         units     => [ "GP" ],
1968         latency   => 1,
1969         mode      => $mode_gp,
1970 },
1971
1972 Conv_I2I => {
1973         op_flags  => [ "fragile" ],
1974         state     => "exc_pinned",
1975         reg_req   => { in => [ "gp", "gp", "none", "gp" ],
1976                        out => [ "gp", "none", "none", "none", "none" ] },
1977         ins       => [ "base", "index", "mem", "val" ],
1978         outs      => [ "res", "flags", "M", "X_regular", "X_except" ],
1979         am        => "source,unary",
1980         units     => [ "GP" ],
1981         latency   => 1,
1982         attr      => "ir_mode *smaller_mode",
1983         init_attr => "attr->ls_mode = smaller_mode;",
1984         mode      => $mode_gp,
1985 },
1986
1987 Conv_I2I8Bit => {
1988         op_flags  => [ "fragile" ],
1989         state     => "exc_pinned",
1990         reg_req   => { in => [ "gp", "gp", "none", "eax ebx ecx edx" ],
1991                        out => [ "gp", "none", "none", "none", "none" ] },
1992         ins       => [ "base", "index", "mem", "val" ],
1993         outs      => [ "res", "flags", "M", "X_regular", "X_except" ],
1994         am        => "source,unary",
1995         units     => [ "GP" ],
1996         latency   => 1,
1997         attr      => "ir_mode *smaller_mode",
1998         init_attr => "attr->ls_mode = smaller_mode;",
1999         mode      => $mode_gp,
2000 },
2001
2002 Conv_I2FP => {
2003         state     => "exc_pinned",
2004         reg_req   => { in => [ "gp", "gp", "none", "gp" ], out => [ "xmm", "none" ] },
2005         ins       => [ "base", "index", "mem", "val" ],
2006         am        => "source,unary",
2007         latency   => 10,
2008         units     => [ "SSE" ],
2009         mode      => $mode_xmm,
2010 },
2011
2012 Conv_FP2I => {
2013         state     => "exc_pinned",
2014         reg_req   => { in => [ "gp", "gp", "none", "xmm" ], out => [ "gp", "none" ] },
2015         ins       => [ "base", "index", "mem", "val" ],
2016         am        => "source,unary",
2017         latency   => 10,
2018         units     => [ "SSE" ],
2019         mode      => $mode_gp,
2020 },
2021
2022 Conv_FP2FP => {
2023         state     => "exc_pinned",
2024         reg_req   => { in => [ "gp", "gp", "none", "xmm" ], out => [ "xmm", "none" ] },
2025         ins       => [ "base", "index", "mem", "val" ],
2026         am        => "source,unary",
2027         latency   => 8,
2028         units     => [ "SSE" ],
2029         mode      => $mode_xmm,
2030 },
2031
2032 # rematerialisation disabled for all float nodes for now, because the fpcw
2033 # handler runs before spilling and we might end up with wrong fpcw then
2034
2035 vfadd => {
2036 #       irn_flags => [ "rematerializable" ],
2037         state     => "exc_pinned",
2038         reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ],
2039                        out => [ "vfp", "none", "none" ] },
2040         ins       => [ "base", "index", "mem", "left", "right", "fpcw" ],
2041         outs      => [ "res", "dummy", "M" ],
2042         am        => "source,binary",
2043         latency   => 4,
2044         units     => [ "VFP" ],
2045         mode      => "mode_E",
2046         attr_type => "ia32_x87_attr_t",
2047 },
2048
2049 vfmul => {
2050 #       irn_flags => [ "rematerializable" ],
2051         state     => "exc_pinned",
2052         reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ],
2053                        out => [ "vfp", "none", "none" ] },
2054         ins       => [ "base", "index", "mem", "left", "right", "fpcw" ],
2055         outs      => [ "res", "dummy", "M" ],
2056         am        => "source,binary",
2057         latency   => 4,
2058         units     => [ "VFP" ],
2059         mode      => "mode_E",
2060         attr_type => "ia32_x87_attr_t",
2061 },
2062
2063 vfsub => {
2064 #       irn_flags => [ "rematerializable" ],
2065         state     => "exc_pinned",
2066         reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ],
2067                        out => [ "vfp", "none", "none" ] },
2068         ins       => [ "base", "index", "mem", "minuend", "subtrahend", "fpcw" ],
2069         outs      => [ "res", "dummy", "M" ],
2070         am        => "source,binary",
2071         latency   => 4,
2072         units     => [ "VFP" ],
2073         mode      => "mode_E",
2074         attr_type => "ia32_x87_attr_t",
2075 },
2076
2077 vfdiv => {
2078         state     => "exc_pinned",
2079         reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ],
2080                        out => [ "vfp", "none", "none" ] },
2081         ins       => [ "base", "index", "mem", "dividend", "divisor", "fpcw" ],
2082         outs      => [ "res", "dummy", "M" ],
2083         am        => "source,binary",
2084         latency   => 20,
2085         units     => [ "VFP" ],
2086         attr_type => "ia32_x87_attr_t",
2087 },
2088
2089 vfprem => {
2090         reg_req   => { in => [ "vfp", "vfp", "fpcw" ], out => [ "vfp" ] },
2091         ins       => [ "left", "right", "fpcw" ],
2092         latency   => 20,
2093         units     => [ "VFP" ],
2094         mode      => "mode_E",
2095         attr_type => "ia32_x87_attr_t",
2096 },
2097
2098 vfabs => {
2099         irn_flags => [ "rematerializable" ],
2100         reg_req   => { in => [ "vfp"], out => [ "vfp" ] },
2101         ins       => [ "value" ],
2102         latency   => 2,
2103         units     => [ "VFP" ],
2104         mode      => "mode_E",
2105         attr_type => "ia32_x87_attr_t",
2106 },
2107
2108 vfchs => {
2109         irn_flags => [ "rematerializable" ],
2110         reg_req   => { in => [ "vfp"], out => [ "vfp" ] },
2111         ins       => [ "value" ],
2112         latency   => 2,
2113         units     => [ "VFP" ],
2114         mode      => "mode_E",
2115         attr_type => "ia32_x87_attr_t",
2116 },
2117
2118 vfld => {
2119         irn_flags => [ "rematerializable" ],
2120         op_flags  => [ "fragile", "labeled" ],
2121         state     => "exc_pinned",
2122         reg_req   => { in => [ "gp", "gp", "none" ],
2123                        out => [ "vfp", "none", "none", "none", "none" ] },
2124         ins       => [ "base", "index", "mem" ],
2125         outs      => [ "res", "unused", "M", "X_regular", "X_except" ],
2126         attr      => "ir_mode *load_mode",
2127         init_attr => "attr->attr.ls_mode = load_mode;",
2128         latency   => 2,
2129         units     => [ "VFP" ],
2130         attr_type => "ia32_x87_attr_t",
2131 },
2132
2133 vfst => {
2134         irn_flags => [ "rematerializable" ],
2135         op_flags  => [ "fragile", "labeled" ],
2136         state     => "exc_pinned",
2137         reg_req   => { in => [ "gp", "gp", "none", "vfp" ],
2138                        out => [ "none", "none", "none" ] },
2139         ins       => [ "base", "index", "mem", "val" ],
2140         outs      => [ "M", "X_regular", "X_except" ],
2141         attr      => "ir_mode *store_mode",
2142         init_attr => "attr->attr.ls_mode = store_mode;",
2143         latency   => 2,
2144         units     => [ "VFP" ],
2145         attr_type => "ia32_x87_attr_t",
2146 },
2147
2148 vfild => {
2149         state     => "exc_pinned",
2150         reg_req   => { in => [ "gp", "gp", "none" ],
2151                        out => [ "vfp", "none", "none" ] },
2152         outs      => [ "res", "unused", "M" ],
2153         ins       => [ "base", "index", "mem" ],
2154         latency   => 4,
2155         units     => [ "VFP" ],
2156         attr_type => "ia32_x87_attr_t",
2157 },
2158
2159 vfist => {
2160         op_flags  => [ "fragile" ],
2161         state     => "exc_pinned",
2162         reg_req   => { in => [ "gp", "gp", "none", "vfp", "fpcw" ],
2163                        out => [ "none", "none", "none", "none" ] },
2164         ins       => [ "base", "index", "mem", "val", "fpcw" ],
2165         outs      => [ "dummy", "M", "X_regular", "X_except" ],
2166         latency   => 4,
2167         units     => [ "VFP" ],
2168         attr_type => "ia32_x87_attr_t",
2169 },
2170
2171 # SSE3 fisttp instruction
2172 vfisttp => {
2173         op_flags  => [ "fragile" ],
2174         state     => "exc_pinned",
2175         reg_req   => { in => [ "gp", "gp", "none", "vfp" ],
2176                        out => [ "in_r4", "none", "none", "none" ]},
2177         ins       => [ "base", "index", "mem", "val" ],
2178         outs      => [ "res", "M", "X_regular", "X_except" ],
2179         latency   => 4,
2180         units     => [ "VFP" ],
2181         attr_type => "ia32_x87_attr_t",
2182 },
2183
2184 vfldz => {
2185         irn_flags => [ "rematerializable" ],
2186         reg_req   => { out => [ "vfp" ] },
2187         outs      => [ "res" ],
2188         latency   => 4,
2189         units     => [ "VFP" ],
2190         mode      => "mode_E",
2191         attr_type => "ia32_x87_attr_t",
2192 },
2193
2194 vfld1 => {
2195         irn_flags => [ "rematerializable" ],
2196         reg_req   => { out => [ "vfp" ] },
2197         outs      => [ "res" ],
2198         latency   => 4,
2199         units     => [ "VFP" ],
2200         mode      => "mode_E",
2201         attr_type => "ia32_x87_attr_t",
2202 },
2203
2204 vfldpi => {
2205         irn_flags => [ "rematerializable" ],
2206         reg_req   => { out => [ "vfp" ] },
2207         outs      => [ "res" ],
2208         latency   => 4,
2209         units     => [ "VFP" ],
2210         mode      => "mode_E",
2211         attr_type => "ia32_x87_attr_t",
2212 },
2213
2214 vfldln2 => {
2215         irn_flags => [ "rematerializable" ],
2216         reg_req   => { out => [ "vfp" ] },
2217         outs      => [ "res" ],
2218         latency   => 4,
2219         units     => [ "VFP" ],
2220         mode      => "mode_E",
2221         attr_type => "ia32_x87_attr_t",
2222 },
2223
2224 vfldlg2 => {
2225         irn_flags => [ "rematerializable" ],
2226         reg_req   => { out => [ "vfp" ] },
2227         outs      => [ "res" ],
2228         latency   => 4,
2229         units     => [ "VFP" ],
2230         mode      => "mode_E",
2231         attr_type => "ia32_x87_attr_t",
2232 },
2233
2234 vfldl2t => {
2235         irn_flags => [ "rematerializable" ],
2236         reg_req   => { out => [ "vfp" ] },
2237         outs      => [ "res" ],
2238         latency   => 4,
2239         units     => [ "VFP" ],
2240         mode      => "mode_E",
2241         attr_type => "ia32_x87_attr_t",
2242 },
2243
2244 vfldl2e => {
2245         irn_flags => [ "rematerializable" ],
2246         reg_req   => { out => [ "vfp" ] },
2247         outs      => [ "res" ],
2248         latency   => 4,
2249         units     => [ "VFP" ],
2250         mode      => "mode_E",
2251         attr_type => "ia32_x87_attr_t",
2252 },
2253
2254 vFucomFnstsw => {
2255 # we can't allow to rematerialize this node so we don't
2256 #  accidently produce Phi(Fucom, Fucom(ins_permuted))
2257 #       irn_flags => [ "rematerializable" ],
2258         reg_req   => { in => [ "vfp", "vfp" ], out => [ "eax" ] },
2259         ins       => [ "left", "right" ],
2260         outs      => [ "flags" ],
2261         attr      => "bool ins_permuted",
2262         init_attr => "attr->attr.data.ins_permuted = ins_permuted;",
2263         latency   => 3,
2264         units     => [ "VFP" ],
2265         attr_type => "ia32_x87_attr_t",
2266         mode      => $mode_gp
2267 },
2268
2269 vFucomi => {
2270         irn_flags => [ "rematerializable" ],
2271         reg_req   => { in => [ "vfp", "vfp" ], out => [ "eflags" ] },
2272         ins       => [ "left", "right" ],
2273         outs      => [ "flags" ],
2274         attr      => "bool ins_permuted",
2275         init_attr => "attr->attr.data.ins_permuted = ins_permuted;",
2276         latency   => 3,
2277         units     => [ "VFP" ],
2278         attr_type => "ia32_x87_attr_t",
2279         mode      => $mode_gp
2280 },
2281
2282 vFtstFnstsw => {
2283 #       irn_flags => [ "rematerializable" ],
2284         reg_req   => { in => [ "vfp" ], out => [ "eax" ] },
2285         ins       => [ "left" ],
2286         outs      => [ "flags" ],
2287         attr      => "bool ins_permuted",
2288         init_attr => "attr->attr.data.ins_permuted = ins_permuted;",
2289         latency   => 3,
2290         units     => [ "VFP" ],
2291         attr_type => "ia32_x87_attr_t",
2292         mode      => $mode_gp
2293 },
2294
2295 Sahf => {
2296         irn_flags => [ "rematerializable" ],
2297         reg_req   => { in => [ "eax" ], out => [ "eflags" ] },
2298         ins       => [ "val" ],
2299         outs      => [ "flags" ],
2300         emit      => '. sahf',
2301         latency   => 1,
2302         units     => [ "GP" ],
2303         mode      => $mode_flags,
2304 },
2305
2306 fadd => {
2307         state     => "exc_pinned",
2308         emit      => '. fadd%XM %x87_binop',
2309         latency   => 4,
2310         attr_type => "ia32_x87_attr_t",
2311         constructors => {},
2312 },
2313
2314 faddp => {
2315         state     => "exc_pinned",
2316         emit      => '. faddp%XM %x87_binop',
2317         latency   => 4,
2318         attr_type => "ia32_x87_attr_t",
2319         constructors => {},
2320 },
2321
2322 fmul => {
2323         state     => "exc_pinned",
2324         emit      => '. fmul%XM %x87_binop',
2325         latency   => 4,
2326         attr_type => "ia32_x87_attr_t",
2327         constructors => {},
2328 },
2329
2330 fmulp => {
2331         state     => "exc_pinned",
2332         emit      => '. fmulp%XM %x87_binop',,
2333         latency   => 4,
2334         attr_type => "ia32_x87_attr_t",
2335         constructors => {},
2336 },
2337
2338 fsub => {
2339         state     => "exc_pinned",
2340         emit      => '. fsub%XM %x87_binop',
2341         latency   => 4,
2342         attr_type => "ia32_x87_attr_t",
2343         constructors => {},
2344 },
2345
2346 # Note: gas is strangely buggy: fdivrp and fdivp as well as fsubrp and fsubp
2347 #       are swapped, we work this around in the emitter...
2348
2349 fsubp => {
2350         state     => "exc_pinned",
2351 # see note about gas bugs
2352         emit      => '. fsubrp%XM %x87_binop',
2353         latency   => 4,
2354         attr_type => "ia32_x87_attr_t",
2355         constructors => {},
2356 },
2357
2358 fsubr => {
2359         state     => "exc_pinned",
2360         irn_flags => [ "rematerializable" ],
2361         emit      => '. fsubr%XM %x87_binop',
2362         latency   => 4,
2363         attr_type => "ia32_x87_attr_t",
2364         constructors => {},
2365 },
2366
2367 fsubrp => {
2368         state     => "exc_pinned",
2369         irn_flags => [ "rematerializable" ],
2370 # see note about gas bugs before fsubp
2371         emit      => '. fsubp%XM %x87_binop',
2372         latency   => 4,
2373         attr_type => "ia32_x87_attr_t",
2374         constructors => {},
2375 },
2376
2377 fprem => {
2378         emit      => '. fprem1',
2379         latency   => 20,
2380         attr_type => "ia32_x87_attr_t",
2381         constructors => {},
2382 },
2383
2384 # this node is just here, to keep the simulator running
2385 # we can omit this when a fprem simulation function exists
2386 fpremp => {
2387         emit      => '. fprem1\n'.
2388                      '. fstp %X0',
2389         latency   => 20,
2390         attr_type => "ia32_x87_attr_t",
2391         constructors => {},
2392 },
2393
2394 fdiv => {
2395         state     => "exc_pinned",
2396         emit      => '. fdiv%XM %x87_binop',
2397         latency   => 20,
2398         attr_type => "ia32_x87_attr_t",
2399         constructors => {},
2400 },
2401
2402 fdivp => {
2403         state     => "exc_pinned",
2404 # see note about gas bugs before fsubp
2405         emit      => '. fdivrp%XM %x87_binop',
2406         latency   => 20,
2407         attr_type => "ia32_x87_attr_t",
2408         constructors => {},
2409 },
2410
2411 fdivr => {
2412         state     => "exc_pinned",
2413         emit      => '. fdivr%XM %x87_binop',
2414         latency   => 20,
2415         attr_type => "ia32_x87_attr_t",
2416         constructors => {},
2417 },
2418
2419 fdivrp => {
2420         state     => "exc_pinned",
2421 # see note about gas bugs before fsubp
2422         emit      => '. fdivp%XM %x87_binop',
2423         latency   => 20,
2424         attr_type => "ia32_x87_attr_t",
2425         constructors => {},
2426 },
2427
2428 fabs => {
2429         emit      => '. fabs',
2430         latency   => 4,
2431         attr_type => "ia32_x87_attr_t",
2432         constructors => {},
2433 },
2434
2435 fchs => {
2436         op_flags  => [ "keep" ],
2437         irn_flags => [ "rematerializable" ],
2438         emit      => '. fchs',
2439         latency   => 4,
2440         attr_type => "ia32_x87_attr_t",
2441         constructors => {},
2442 },
2443
2444 fld => {
2445         irn_flags => [ "rematerializable" ],
2446         op_flags  => [ "labeled" ],
2447         state     => "exc_pinned",
2448         emit      => '. fld%XM %AM',
2449         attr_type => "ia32_x87_attr_t",
2450         latency   => 2,
2451         constructors => {},
2452 },
2453
2454 fst => {
2455         irn_flags => [ "rematerializable" ],
2456         op_flags  => [ "labeled" ],
2457         state     => "exc_pinned",
2458         emit      => '. fst%XM %AM',
2459         mode      => "mode_M",
2460         attr_type => "ia32_x87_attr_t",
2461         latency   => 2,
2462         constructors => {},
2463 },
2464
2465 fstp => {
2466         irn_flags => [ "rematerializable" ],
2467         op_flags  => [ "labeled" ],
2468         state     => "exc_pinned",
2469         emit      => '. fstp%XM %AM',
2470         mode      => "mode_M",
2471         attr_type => "ia32_x87_attr_t",
2472         latency   => 2,
2473         constructors => {},
2474 },
2475
2476 fild => {
2477         state     => "exc_pinned",
2478         emit      => '. fild%XM %AM',
2479         attr_type => "ia32_x87_attr_t",
2480         latency   => 2,
2481         constructors => {},
2482 },
2483
2484 fist => {
2485         state     => "exc_pinned",
2486         emit      => '. fist%XM %AM',
2487         mode      => "mode_M",
2488         attr_type => "ia32_x87_attr_t",
2489         latency   => 2,
2490         constructors => {},
2491 },
2492
2493 fistp => {
2494         state     => "exc_pinned",
2495         emit      => '. fistp%XM %AM',
2496         mode      => "mode_M",
2497         attr_type => "ia32_x87_attr_t",
2498         latency   => 2,
2499         constructors => {},
2500 },
2501
2502 # SSE3 fisttp instruction
2503 fisttp => {
2504         state     => "exc_pinned",
2505         emit      => '. fisttp%XM %AM',
2506         mode      => "mode_M",
2507         attr_type => "ia32_x87_attr_t",
2508         latency   => 2,
2509         constructors => {},
2510 },
2511
2512 fldz => {
2513         op_flags  =>  [ "constlike", "keep" ],
2514         irn_flags => [ "rematerializable" ],
2515         reg_req   => { out => [ "vfp" ] },
2516         emit      => '. fldz',
2517         attr_type => "ia32_x87_attr_t",
2518         latency   => 2,
2519 },
2520
2521 fld1 => {
2522         op_flags  => [ "constlike", "keep" ],
2523         irn_flags => [ "rematerializable" ],
2524         reg_req   => { out => [ "vfp" ] },
2525         emit      => '. fld1',
2526         attr_type => "ia32_x87_attr_t",
2527         latency   => 2,
2528 },
2529
2530 fldpi => {
2531         op_flags  => [ "constlike", "keep" ],
2532         irn_flags => [ "rematerializable" ],
2533         reg_req   => { out => [ "vfp" ] },
2534         emit      => '. fldpi',
2535         attr_type => "ia32_x87_attr_t",
2536         latency   => 2,
2537 },
2538
2539 fldln2 => {
2540         op_flags  => [ "constlike", "keep" ],
2541         irn_flags => [ "rematerializable" ],
2542         reg_req   => { out => [ "vfp" ] },
2543         emit      => '. fldln2',
2544         attr_type => "ia32_x87_attr_t",
2545         latency   => 2,
2546 },
2547
2548 fldlg2 => {
2549         op_flags  => [ "constlike", "keep" ],
2550         irn_flags => [ "rematerializable" ],
2551         reg_req   => { out => [ "vfp" ] },
2552         emit      => '. fldlg2',
2553         attr_type => "ia32_x87_attr_t",
2554         latency   => 2,
2555 },
2556
2557 fldl2t => {
2558         op_flags  => [ "constlike", "keep" ],
2559         irn_flags => [ "rematerializable" ],
2560         reg_req   => { out => [ "vfp" ] },
2561         emit      => '. fldll2t',
2562         attr_type => "ia32_x87_attr_t",
2563         latency   => 2,
2564 },
2565
2566 fldl2e => {
2567         op_flags  => [ "constlike", "keep" ],
2568         irn_flags => [ "rematerializable" ],
2569         reg_req   => { out => [ "vfp" ] },
2570         emit      => '. fldl2e',
2571         attr_type => "ia32_x87_attr_t",
2572         latency   => 2,
2573 },
2574
2575 # fxch, fpush, fpop
2576 # Note that it is NEVER allowed to do CSE on these nodes
2577 # Moreover, note the virtual register requierements!
2578
2579 fxch => {
2580         op_flags  => [ "keep" ],
2581         reg_req   => { out => [ "none" ] },
2582         cmp_attr  => "return 1;",
2583         emit      => '. fxch %X0',
2584         attr_type => "ia32_x87_attr_t",
2585         mode      => "mode_ANY",
2586         latency   => 1,
2587 },
2588
2589 fpush => {
2590         op_flags  => [ "keep" ],
2591         reg_req   => { out => [ "none" ] },
2592         cmp_attr  => "return 1;",
2593         emit      => '. fld %X0',
2594         attr_type => "ia32_x87_attr_t",
2595         mode      => "mode_ANY",
2596         latency   => 1,
2597 },
2598
2599 fpushCopy => {
2600         reg_req   => { in => [ "vfp"], out => [ "vfp" ] },
2601         cmp_attr  => "return 1;",
2602         emit      => '. fld %X0',
2603         attr_type => "ia32_x87_attr_t",
2604         latency   => 1,
2605 },
2606
2607 fpop => {
2608         op_flags  => [ "keep" ],
2609         reg_req   => { out => [ "none" ] },
2610         cmp_attr  => "return 1;",
2611         emit      => '. fstp %X0',
2612         attr_type => "ia32_x87_attr_t",
2613         mode      => "mode_ANY",
2614         latency   => 1,
2615 },
2616
2617 ffreep => {
2618         op_flags  => [ "keep" ],
2619         reg_req   => { out => [ "none" ] },
2620         cmp_attr  => "return 1;",
2621         emit      => '. ffreep %X0',
2622         attr_type => "ia32_x87_attr_t",
2623         mode      => "mode_ANY",
2624         latency   => 1,
2625 },
2626
2627 emms => {
2628         op_flags  => [ "keep" ],
2629         reg_req   => { out => [ "none" ] },
2630         cmp_attr  => "return 1;",
2631         emit      => '. emms',
2632         attr_type => "ia32_x87_attr_t",
2633         mode      => "mode_ANY",
2634         latency   => 3,
2635 },
2636
2637 femms => {
2638         op_flags  => [ "keep" ],
2639         reg_req   => { out => [ "none" ] },
2640         cmp_attr  => "return 1;",
2641         emit      => '. femms',
2642         attr_type => "ia32_x87_attr_t",
2643         mode      => "mode_ANY",
2644         latency   => 3,
2645 },
2646
2647 FucomFnstsw => {
2648         reg_req   => { },
2649         emit      => ". fucom %X1\n".
2650                      ". fnstsw %%ax",
2651         attr_type => "ia32_x87_attr_t",
2652         latency   => 2,
2653 },
2654
2655 FucompFnstsw => {
2656         reg_req   => { },
2657         emit      => ". fucomp %X1\n".
2658                      ". fnstsw %%ax",
2659         attr_type => "ia32_x87_attr_t",
2660         latency   => 2,
2661 },
2662
2663 FucomppFnstsw => {
2664         reg_req   => { },
2665         emit      => ". fucompp\n".
2666                      ". fnstsw %%ax",
2667         attr_type => "ia32_x87_attr_t",
2668         latency   => 2,
2669 },
2670
2671 Fucomi => {
2672         reg_req   => { },
2673         emit      => '. fucomi %X1',
2674         attr_type => "ia32_x87_attr_t",
2675         latency   => 1,
2676 },
2677
2678 Fucompi => {
2679         reg_req   => { },
2680         emit      => '. fucompi %X1',
2681         attr_type => "ia32_x87_attr_t",
2682         latency   => 1,
2683 },
2684
2685 FtstFnstsw => {
2686         reg_req   => { },
2687         emit      => ". ftst\n".
2688                      ". fnstsw %%ax",
2689         attr_type => "ia32_x87_attr_t",
2690         latency   => 2,
2691 },
2692
2693 # Spilling and reloading of SSE registers, hardcoded, not generated #
2694
2695 xxLoad => {
2696         op_flags  => [ "fragile", "labeled" ],
2697         state     => "exc_pinned",
2698         reg_req   => { in => [ "gp", "gp", "none" ],
2699                        out => [ "xmm", "none", "none", "none" ] },
2700         emit      => '. movdqu %D0, %AM',
2701         ins       => [ "base", "index", "mem" ],
2702         outs      => [ "res", "M", "X_regular", "X_except" ],
2703         units     => [ "SSE" ],
2704         latency   => 1,
2705 },
2706
2707 xxStore => {
2708         op_flags => [ "fragile", "labeled" ],
2709         state    => "exc_pinned",
2710         reg_req  => { in => [ "gp", "gp", "none", "xmm" ],
2711                       out => [ "none", "none", "none" ] },
2712         ins      => [ "base", "index", "mem", "val" ],
2713         outs     => [ "M", "X_regular", "X_except" ],
2714         emit     => '. movdqu %binop',
2715         units    => [ "SSE" ],
2716         latency  => 1,
2717 },
2718
2719 ); # end of %nodes
2720
2721 # Transform some attributes
2722 foreach my $op (keys(%nodes)) {
2723         my $node         = $nodes{$op};
2724         my $op_attr_init = $node->{op_attr_init};
2725
2726         if(defined($op_attr_init)) {
2727                 $op_attr_init .= "\n\t";
2728         } else {
2729                 $op_attr_init = "";
2730         }
2731
2732         if(!defined($node->{latency})) {
2733                 if($op =~ m/^l_/) {
2734                         $node->{latency} = 0;
2735                 } else {
2736                         die("Latency missing for op $op");
2737                 }
2738         }
2739         $op_attr_init .= "attr->latency = ".$node->{latency} . ";";
2740
2741         $node->{op_attr_init} = $op_attr_init;
2742 }
2743
2744 print "";