http://gcc.gnu.org/bugzilla/show_bug.cgi?id=59390

--- Comment #4 from Sriraman Tallam <tmsriram at google dot com> ---
Here is the problem. GCC adds target-specific builtins on demand. The FMA
target-specific builtin __builtin_ia32_vfmaddpd gets added via this
declaration:

void fun() __attribute__((target("fma")));

Specifically, the builtin __builtin_ia32_vfmaddpd gets added when
ix86_add_new_builtins is called from ix86_valid_target_attribute_tree when
processing this target attribute.

Now, when the vectorizer is processing the builtin "__builtin_fma" in function
other_fn(), it checks to see if this function is vectorizable and calls
ix86_builtin_vectorized_function in i386.c. That returns the builtin stored
here:


   case BUILT_IN_FMA:
      if (out_mode == DFmode && in_mode == DFmode)
    {
      if (out_n == 2 && in_n == 2)
        return ix86_builtins[IX86_BUILTIN_VFMADDPD];
          ....

ix86_builtins[IX86_BUILTIN_VFMADDPD] would have contained NULL_TREE had the
builtin not been added by the previous target attribute. That is why the code
works if we remove the previous declaration.

The fix then is to not just return the builtin but to also check if the current
function's isa allows the use of the builtin. For instance, this patch would
solve the problem:

@@ -33977,7 +33977,13 @@ ix86_builtin_vectorized_function (tree fndecl, tre
       if (out_mode == DFmode && in_mode == DFmode)
     {
       if (out_n == 2 && in_n == 2)
-        return ix86_builtins[IX86_BUILTIN_VFMADDPD];
+        {
+          if (ix86_builtins_isa[IX86_BUILTIN_VFMADDPD].isa
+          & global_options.x_ix86_isa_flags)
+            return ix86_builtins[IX86_BUILTIN_VFMADDPD];
+          else
+        return NULL_TREE;
+        }


but there are many instances of this usage in ix86_builtin_vectorized_function.
I will make a patch to cover all these cases and send for review.

Reply via email to