As a reminiscence to the famous MAC/65 assembler changed modifier + into > and -...
[libfirm] / ir / be / ia32 / ia32_spec.pl
index c16d787..a49559d 100644 (file)
@@ -4,7 +4,6 @@
 
 use File::Basename;
 
-$new_emit_syntax = 1;
 my $myname = $0;
 
 # the cpu architecture (ia32, ia64, mips, sparc, ppc, ...)
@@ -34,7 +33,6 @@ $arch = "ia32";
 #   emit      => "emit code with templates",
 #   attr      => "additional attribute arguments for constructor",
 #   init_attr => "emit attribute initialization template",
-#   rd_constructor => "c source code which constructs an ir_node",
 #   hash_func => "name of the hash function for this operation",
 #   latency   => "latency of this operation (can be float)"
 #   attr_type => "name of the attribute struct",
@@ -226,25 +224,18 @@ $arch = "ia32";
        CMP3  => "${arch}_emit_cmp_suffix_node(node, 3);",
 );
 
-#--------------------------------------------------#
-#                        _                         #
-#                       (_)                        #
-#  _ __   _____      __  _ _ __    ___  _ __  ___  #
-# | '_ \ / _ \ \ /\ / / | | '__|  / _ \| '_ \/ __| #
-# | | | |  __/\ V  V /  | | |    | (_) | |_) \__ \ #
-# |_| |_|\___| \_/\_/   |_|_|     \___/| .__/|___/ #
-#                                      | |         #
-#                                      |_|         #
-#--------------------------------------------------#
+
+
 
 $default_op_attr_type = "ia32_op_attr_t";
 $default_attr_type    = "ia32_attr_t";
 $default_copy_attr    = "ia32_copy_attr";
 
 sub ia32_custom_init_attr {
-       my $node = shift;
-       my $name = shift;
-       my $res = "";
+       my $constr = shift;
+       my $node   = shift;
+       my $name   = shift;
+       my $res    = "";
 
        if(defined($node->{modified_flags})) {
                $res .= "\tarch_irn_add_flags(res, arch_irn_flags_modify_flags);\n";
@@ -358,19 +349,6 @@ ProduceVal => {
        cmp_attr  => "return 1;",
 },
 
-#-----------------------------------------------------------------#
-#  _       _                                         _            #
-# (_)     | |                                       | |           #
-#  _ _ __ | |_ ___  __ _  ___ _ __   _ __   ___   __| | ___  ___  #
-# | | '_ \| __/ _ \/ _` |/ _ \ '__| | '_ \ / _ \ / _` |/ _ \/ __| #
-# | | | | | ||  __/ (_| |  __/ |    | | | | (_) | (_| |  __/\__ \ #
-# |_|_| |_|\__\___|\__, |\___|_|    |_| |_|\___/ \__,_|\___||___/ #
-#                   __/ |                                         #
-#                  |___/                                          #
-#-----------------------------------------------------------------#
-
-# commutative operations
-
 Add => {
        irn_flags => "R",
        state     => "exc_pinned",
@@ -507,7 +485,6 @@ And => {
                           out => [ "in_r4 in_r5", "flags", "none" ] },
        ins       => [ "base", "index", "mem", "left", "right" ],
        outs      => [ "res", "flags", "M" ],
-       op_modes  => "commutative | am | immediate | mode_neutral",
        am        => "source,binary",
        emit      => '. and%M %binop',
        units     => [ "GP" ],
@@ -630,8 +607,6 @@ XorMem8Bit => {
        modified_flags => $status_flags
 },
 
-# not commutative operations
-
 Sub => {
        irn_flags => "R",
        state     => "exc_pinned",
@@ -915,8 +890,6 @@ RolMem => {
        modified_flags => $status_flags
 },
 
-# unary operations
-
 Neg => {
        irn_flags => "R",
        reg_req   => { in => [ "gp" ],
@@ -1028,8 +1001,8 @@ NotMem => {
 },
 
 Cmc => {
-       reg_req => { in => [ "flags" ], out => [ "flags" ] },
-       emit    => '.cmc',
+       reg_req   => { in => [ "flags" ], out => [ "flags" ] },
+       emit      => '.cmc',
        units     => [ "GP" ],
        latency   => 1,
        mode      => $mode_flags,
@@ -1037,16 +1010,14 @@ Cmc => {
 },
 
 Stc => {
-       reg_req => { out => [ "flags" ] },
-       emit    => '.stc',
+       reg_req   => { out => [ "flags" ] },
+       emit      => '.stc',
        units     => [ "GP" ],
        latency   => 1,
        mode      => $mode_flags,
        modified_flags => $status_flags
 },
 
-# other operations
-
 Cmp => {
        irn_flags => "R",
        state     => "exc_pinned",
@@ -1119,36 +1090,34 @@ Test8Bit => {
        modified_flags => $status_flags
 },
 
-Set => {
+Setcc => {
        #irn_flags => "R",
        reg_req   => { in => [ "eflags" ], out => [ "eax ebx ecx edx" ] },
        ins       => [ "eflags" ],
+       outs      => [ "res" ],
        attr_type => "ia32_condcode_attr_t",
-       attr      => "pn_Cmp pnc, int ins_permuted",
-       init_attr => "attr->attr.data.ins_permuted = ins_permuted;\n".
-                     "\tset_ia32_ls_mode(res, mode_Bu);\n",
-       emit      => '. set%CMP0 %DB0',
+       attr      => "pn_Cmp pnc",
+       init_attr => "set_ia32_ls_mode(res, mode_Bu);\n",
        latency   => 1,
        units     => [ "GP" ],
        mode      => $mode_gp,
 },
 
-SetMem => {
+SetccMem => {
        #irn_flags => "R",
        state     => "exc_pinned",
        reg_req   => { in => [ "gp", "gp", "none", "eflags" ], out => [ "none" ] },
        ins       => [ "base", "index", "mem","eflags" ],
        attr_type => "ia32_condcode_attr_t",
-       attr      => "pn_Cmp pnc, int ins_permuted",
-       init_attr => "attr->attr.data.ins_permuted = ins_permuted;\n".
-                     "\tset_ia32_ls_mode(res, mode_Bu);\n",
+       attr      => "pn_Cmp pnc",
+       init_attr => "set_ia32_ls_mode(res, mode_Bu);\n",
        emit      => '. set%CMP3 %AM',
        latency   => 1,
        units     => [ "GP" ],
        mode      => 'mode_M',
 },
 
-CMov => {
+CMovcc => {
        #irn_flags => "R",
        # (note: leave the false,true order intact to make it compatible with other
        #  ia32_binary ops)
@@ -1188,16 +1157,17 @@ SwitchJmp => {
        latency   => 3,
        units     => [ "BRANCH" ],
        modified_flags => $status_flags,
-       init_attr => "info->out_infos = NULL;",
+       init_attr => "info->out_infos = NULL;", # XXX ugly hack for out requirements
 },
 
 Jmp => {
-       state    => "pinned",
-       op_flags => "X",
-       reg_req  => { out => [ "none" ] },
-       latency  => 1,
-       units    => [ "BRANCH" ],
-       mode     => "mode_X",
+       state     => "pinned",
+       irn_flags => "J",
+       op_flags  => "X",
+       reg_req   => { out => [ "none" ] },
+       latency   => 1,
+       units     => [ "BRANCH" ],
+       mode      => "mode_X",
 },
 
 IJmp => {
@@ -1210,6 +1180,7 @@ IJmp => {
        latency   => 1,
        units     => [ "BRANCH" ],
        mode      => "mode_X",
+       init_attr => "info->out_infos = NULL;", # XXX ugly hack for out requirements
 },
 
 Const => {
@@ -1750,15 +1721,6 @@ PrefetchW => {
        units     => [ "GP" ],
 },
 
-#-----------------------------------------------------------------------------#
-#   _____ _____ ______    __ _             _                     _            #
-#  / ____/ ____|  ____|  / _| |           | |                   | |           #
-# | (___| (___ | |__    | |_| | ___   __ _| |_   _ __   ___   __| | ___  ___  #
-#  \___ \\___ \|  __|   |  _| |/ _ \ / _` | __| | '_ \ / _ \ / _` |/ _ \/ __| #
-#  ____) |___) | |____  | | | | (_) | (_| | |_  | | | | (_) | (_| |  __/\__ \ #
-# |_____/_____/|______| |_| |_|\___/ \__,_|\__| |_| |_|\___/ \__,_|\___||___/ #
-#-----------------------------------------------------------------------------#
-
 # produces a 0/+0.0
 xZero => {
        irn_flags => "R",
@@ -1828,8 +1790,6 @@ xMovd  => {
        mode      => $mode_xmm
 },
 
-# commutative operations
-
 xAdd => {
        irn_flags => "R",
        state     => "exc_pinned",
@@ -1928,8 +1888,6 @@ xXor => {
        mode      => $mode_xmm
 },
 
-# not commutative operations
-
 xAndNot => {
        irn_flags => "R",
        state     => "exc_pinned",
@@ -1971,8 +1929,6 @@ xDiv => {
        units     => [ "SSE" ],
 },
 
-# other operations
-
 Ucomi => {
        irn_flags => "R",
        state     => "exc_pinned",
@@ -1990,8 +1946,6 @@ Ucomi => {
        modified_flags => 1,
 },
 
-# Load / Store
-
 xLoad => {
        op_flags  => "L|F",
        state     => "exc_pinned",
@@ -2070,8 +2024,6 @@ l_FloattoLL => {
        reg_req  => { in => [ "none" ], out => [ "none", "none" ] }
 },
 
-# CopyB
-
 CopyB => {
        op_flags  => "F|H",
        state     => "pinned",
@@ -2098,8 +2050,6 @@ CopyB_i => {
 #      modified_flags => [ "DF" ]
 },
 
-# Conversions
-
 Cwtl => {
        state     => "exc_pinned",
        reg_req   => { in => [ "eax" ], out => [ "eax" ] },
@@ -2169,28 +2119,16 @@ Conv_FP2FP => {
        mode      => $mode_xmm,
 },
 
-#----------------------------------------------------------#
-#        _      _               _    __ _             _    #
-#       (_)    | |             | |  / _| |           | |   #
-# __   ___ _ __| |_ _   _  __ _| | | |_| | ___   __ _| |_  #
-# \ \ / / | '__| __| | | |/ _` | | |  _| |/ _ \ / _` | __| #
-#  \ V /| | |  | |_| |_| | (_| | | | | | | (_) | (_| | |_  #
-#   \_/ |_|_|   \__|\__,_|\__,_|_| |_| |_|\___/ \__,_|\__| #
-#                 | |                                      #
-#  _ __   ___   __| | ___  ___                             #
-# | '_ \ / _ \ / _` |/ _ \/ __|                            #
-# | | | | (_) | (_| |  __/\__ \                            #
-# |_| |_|\___/ \__,_|\___||___/                            #
-#----------------------------------------------------------#
-
 # rematerialisation disabled for all float nodes for now, because the fpcw
 # handler runs before spilling and we might end up with wrong fpcw then
 
 vfadd => {
 #      irn_flags => "R",
        state     => "exc_pinned",
-       reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ], out => [ "vfp" ] },
+       reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ],
+                      out => [ "vfp", "none", "none" ] },
        ins       => [ "base", "index", "mem", "left", "right", "fpcw" ],
+       outs      => [ "res", "dummy", "M" ],
        am        => "source,binary",
        latency   => 4,
        units     => [ "VFP" ],
@@ -2201,8 +2139,10 @@ vfadd => {
 vfmul => {
 #      irn_flags => "R",
        state     => "exc_pinned",
-       reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ], out => [ "vfp" ] },
+       reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ],
+                      out => [ "vfp", "none", "none" ] },
        ins       => [ "base", "index", "mem", "left", "right", "fpcw" ],
+       outs      => [ "res", "dummy", "M" ],
        am        => "source,binary",
        latency   => 4,
        units     => [ "VFP" ],
@@ -2213,8 +2153,10 @@ vfmul => {
 vfsub => {
 #      irn_flags => "R",
        state     => "exc_pinned",
-       reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ], out => [ "vfp" ] },
+       reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ],
+                      out => [ "vfp", "none", "none" ] },
        ins       => [ "base", "index", "mem", "minuend", "subtrahend", "fpcw" ],
+       outs      => [ "res", "dummy", "M" ],
        am        => "source,binary",
        latency   => 4,
        units     => [ "VFP" ],
@@ -2224,10 +2166,11 @@ vfsub => {
 
 vfdiv => {
        state     => "exc_pinned",
-       reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ], out => [ "vfp", "none" ] },
+       reg_req   => { in => [ "gp", "gp", "none", "vfp", "vfp", "fpcw" ],
+                      out => [ "vfp", "none", "none" ] },
        ins       => [ "base", "index", "mem", "dividend", "divisor", "fpcw" ],
+       outs      => [ "res", "dummy", "M" ],
        am        => "source,binary",
-       outs      => [ "res", "M" ],
        latency   => 20,
        units     => [ "VFP" ],
        attr_type => "ia32_x87_attr_t",
@@ -2262,8 +2205,6 @@ vfchs => {
        attr_type => "ia32_x87_attr_t",
 },
 
-# virtual Load and Store
-
 vfld => {
        irn_flags => "R",
        op_flags  => "L|F",
@@ -2295,8 +2236,6 @@ vfst => {
        attr_type => "ia32_x87_attr_t",
 },
 
-# Conversions
-
 vfild => {
        state     => "exc_pinned",
        reg_req   => { in => [ "gp", "gp", "none" ],
@@ -2330,9 +2269,6 @@ vfisttp => {
        attr_type => "ia32_x87_attr_t",
 },
 
-
-# constants
-
 vfldz => {
        irn_flags => "R",
        reg_req   => { out => [ "vfp" ] },
@@ -2403,10 +2339,8 @@ vfldl2e => {
        attr_type => "ia32_x87_attr_t",
 },
 
-# other
-
 vFucomFnstsw => {
-# we can't allow to rematerialize this node so we don't have
+# we can't allow to rematerialize this node so we don't
 #  accidently produce Phi(Fucom, Fucom(ins_permuted))
 #      irn_flags => "R",
        reg_req   => { in => [ "vfp", "vfp" ], out => [ "eax" ] },
@@ -2457,245 +2391,208 @@ Sahf => {
        mode      => $mode_flags,
 },
 
-#------------------------------------------------------------------------#
-#       ___ _____    __ _             _                     _            #
-# __  _( _ )___  |  / _| | ___   __ _| |_   _ __   ___   __| | ___  ___  #
-# \ \/ / _ \  / /  | |_| |/ _ \ / _` | __| | '_ \ / _ \ / _` |/ _ \/ __| #
-#  >  < (_) |/ /   |  _| | (_) | (_| | |_  | | | | (_) | (_| |  __/\__ \ #
-# /_/\_\___//_/    |_| |_|\___/ \__,_|\__| |_| |_|\___/ \__,_|\___||___/ #
-#------------------------------------------------------------------------#
-
-# Note: gas is strangely buggy: fdivrp and fdivp as well as fsubrp and fsubp
-#       are swapped, we work this around in the emitter...
-
 fadd => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fadd%XM %x87_binop',
        latency   => 4,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 faddp => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. faddp%XM %x87_binop',
        latency   => 4,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fmul => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fmul%XM %x87_binop',
        latency   => 4,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fmulp => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fmulp%XM %x87_binop',,
        latency   => 4,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fsub => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fsub%XM %x87_binop',
        latency   => 4,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
+# Note: gas is strangely buggy: fdivrp and fdivp as well as fsubrp and fsubp
+#       are swapped, we work this around in the emitter...
+
 fsubp => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
 # see note about gas bugs
        emit      => '. fsubrp%XM %x87_binop',
        latency   => 4,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fsubr => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
        irn_flags => "R",
-       reg_req   => { },
        emit      => '. fsubr%XM %x87_binop',
        latency   => 4,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fsubrp => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
        irn_flags => "R",
-       reg_req   => { },
-# see note about gas bugs
+# see note about gas bugs before fsubp
        emit      => '. fsubp%XM %x87_binop',
        latency   => 4,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fprem => {
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fprem1',
        latency   => 20,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 # this node is just here, to keep the simulator running
 # we can omit this when a fprem simulation function exists
 fpremp => {
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fprem1\n'.
                     '. fstp %X0',
        latency   => 20,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fdiv => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fdiv%XM %x87_binop',
        latency   => 20,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fdivp => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
-# see note about gas bugs
+# see note about gas bugs before fsubp
        emit      => '. fdivrp%XM %x87_binop',
        latency   => 20,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fdivr => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fdivr%XM %x87_binop',
        latency   => 20,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fdivrp => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
-# see note about gas bugs
+# see note about gas bugs before fsubp
        emit      => '. fdivp%XM %x87_binop',
        latency   => 20,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fabs => {
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fabs',
        latency   => 4,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
 fchs => {
        op_flags  => "R|K",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fchs',
        latency   => 4,
        attr_type => "ia32_x87_attr_t",
+       constructors => {},
 },
 
-# x87 Load and Store
-
 fld => {
-       rd_constructor => "NONE",
        op_flags  => "R|L|F",
        state     => "exc_pinned",
-       reg_req   => { },
        emit      => '. fld%XM %AM',
        attr_type => "ia32_x87_attr_t",
        latency   => 2,
+       constructors => {},
 },
 
 fst => {
-       rd_constructor => "NONE",
        op_flags  => "R|L|F",
        state     => "exc_pinned",
-       reg_req   => { },
        emit      => '. fst%XM %AM',
        mode      => "mode_M",
        attr_type => "ia32_x87_attr_t",
        latency   => 2,
+       constructors => {},
 },
 
 fstp => {
-       rd_constructor => "NONE",
        op_flags  => "R|L|F",
        state     => "exc_pinned",
-       reg_req   => { },
        emit      => '. fstp%XM %AM',
        mode      => "mode_M",
        attr_type => "ia32_x87_attr_t",
        latency   => 2,
+       constructors => {},
 },
 
-# Conversions
-
 fild => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fild%XM %AM',
        attr_type => "ia32_x87_attr_t",
        latency   => 2,
+       constructors => {},
 },
 
 fist => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fist%XM %AM',
        mode      => "mode_M",
        attr_type => "ia32_x87_attr_t",
        latency   => 2,
+       constructors => {},
 },
 
 fistp => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fistp%XM %AM',
        mode      => "mode_M",
        attr_type => "ia32_x87_attr_t",
        latency   => 2,
+       constructors => {},
 },
 
 # SSE3 fisttp instruction
 fisttp => {
        state     => "exc_pinned",
-       rd_constructor => "NONE",
-       reg_req   => { },
        emit      => '. fisttp%XM %AM',
        mode      => "mode_M",
        attr_type => "ia32_x87_attr_t",
        latency   => 2,
+       constructors => {},
 },
 
-# constants
-
 fldz => {
        op_flags  => "R|c|K",
        irn_flags => "R",
@@ -2831,8 +2728,6 @@ femms => {
        latency   => 3,
 },
 
-# compare
-
 FucomFnstsw => {
        reg_req   => { },
        emit      => ". fucom %X1\n".
@@ -2879,17 +2774,6 @@ FtstFnstsw => {
        latency   => 2,
 },
 
-
-# -------------------------------------------------------------------------------- #
-#  ____ ____  _____                  _                               _             #
-# / ___/ ___|| ____| __   _____  ___| |_ ___  _ __   _ __   ___   __| | ___  ___   #
-# \___ \___ \|  _|   \ \ / / _ \/ __| __/ _ \| '__| | '_ \ / _ \ / _` |/ _ \/ __|  #
-#  ___) |__) | |___   \ V /  __/ (__| || (_) | |    | | | | (_) | (_| |  __/\__ \  #
-# |____/____/|_____|   \_/ \___|\___|\__\___/|_|    |_| |_|\___/ \__,_|\___||___/  #
-#                                                                                  #
-# -------------------------------------------------------------------------------- #
-
-
 # Spilling and reloading of SSE registers, hardcoded, not generated #
 
 xxLoad => {
@@ -2915,14 +2799,6 @@ xxStore => {
 
 ); # end of %nodes
 
-# Include the generated SIMD node specification written by the SIMD optimization
-$my_script_name = dirname($myname) . "/../ia32/ia32_simd_spec.pl";
-unless ($return = do $my_script_name) {
-       warn "couldn't parse $my_script_name: $@" if $@;
-       warn "couldn't do $my_script_name: $!"    unless defined $return;
-       warn "couldn't run $my_script_name"       unless $return;
-}
-
 # Transform some attributes
 foreach my $op (keys(%nodes)) {
        my $node         = $nodes{$op};