Index: cfe/trunk/docs/ClangCommandLineReference.rst =================================================================== --- cfe/trunk/docs/ClangCommandLineReference.rst +++ cfe/trunk/docs/ClangCommandLineReference.rst @@ -2120,6 +2120,10 @@ Use copy relocations support for PIE builds +.. option:: -mprefer-vector-width= + +Specifies preferred vector width for auto-vectorization. Defaults to 'none' which allows target specific decisions. + .. option:: -mqdsp6-compat Enable hexagon-qdsp6 backward compatibility Index: cfe/trunk/include/clang/Driver/Options.td =================================================================== --- cfe/trunk/include/clang/Driver/Options.td +++ cfe/trunk/include/clang/Driver/Options.td @@ -1954,6 +1954,8 @@ def mimplicit_float : Flag<["-"], "mimplicit-float">, Group; def mrecip : Flag<["-"], "mrecip">, Group; def mrecip_EQ : CommaJoined<["-"], "mrecip=">, Group, Flags<[CC1Option]>; +def mprefer_vector_width_EQ : Joined<["-"], "mprefer-vector-width=">, Group, Flags<[CC1Option]>, + HelpText<"Specifies preferred vector width for auto-vectorization. Defaults to 'none' which allows target specific decisions.">; def mpie_copy_relocations : Flag<["-"], "mpie-copy-relocations">, Group, Flags<[CC1Option]>, HelpText<"Use copy relocations support for PIE builds">; Index: cfe/trunk/include/clang/Frontend/CodeGenOptions.h =================================================================== --- cfe/trunk/include/clang/Frontend/CodeGenOptions.h +++ cfe/trunk/include/clang/Frontend/CodeGenOptions.h @@ -253,6 +253,11 @@ std::vector Reciprocals; + /// The preferred width for auto-vectorization transforms. This is intended to + /// override default transforms based on the width of the architected vector + /// registers. + std::string PreferVectorWidth; + public: // Define accessors/mutators for code generation options of enumeration type. #define CODEGENOPT(Name, Bits, Default) Index: cfe/trunk/lib/CodeGen/CGCall.cpp =================================================================== --- cfe/trunk/lib/CodeGen/CGCall.cpp +++ cfe/trunk/lib/CodeGen/CGCall.cpp @@ -1744,6 +1744,11 @@ FuncAttrs.addAttribute("reciprocal-estimates", llvm::join(Recips, ",")); + if (!CodeGenOpts.PreferVectorWidth.empty() && + CodeGenOpts.PreferVectorWidth != "none") + FuncAttrs.addAttribute("prefer-vector-width", + CodeGenOpts.PreferVectorWidth); + if (CodeGenOpts.StackRealignment) FuncAttrs.addAttribute("stackrealign"); if (CodeGenOpts.Backchain) Index: cfe/trunk/lib/Driver/ToolChains/Clang.cpp =================================================================== --- cfe/trunk/lib/Driver/ToolChains/Clang.cpp +++ cfe/trunk/lib/Driver/ToolChains/Clang.cpp @@ -274,6 +274,27 @@ OutStrings.push_back(Args.MakeArgString(Out)); } +/// The -mprefer-vector-width option accepts either a positive integer +/// or the string "none". +static void ParseMPreferVectorWidth(const Driver &D, const ArgList &Args, + ArgStringList &CmdArgs) { + Arg *A = Args.getLastArg(options::OPT_mprefer_vector_width_EQ); + if (!A) + return; + + StringRef Value = A->getValue(); + if (Value == "none") { + CmdArgs.push_back("-mprefer-vector-width=none"); + } else { + unsigned Width; + if (Value.getAsInteger(10, Width)) { + D.Diag(diag::err_drv_invalid_value) << A->getOption().getName() << Value; + return; + } + CmdArgs.push_back(Args.MakeArgString("-mprefer-vector-width=" + Value)); + } +} + static void getWebAssemblyTargetFeatures(const ArgList &Args, std::vector &Features) { handleTargetFeaturesGroup(Args, Features, options::OPT_m_wasm_Features_Group); @@ -4333,6 +4354,8 @@ options::OPT_fno_slp_vectorize, EnableSLPVec)) CmdArgs.push_back("-vectorize-slp"); + ParseMPreferVectorWidth(D, Args, CmdArgs); + if (Arg *A = Args.getLastArg(options::OPT_fshow_overloads_EQ)) A->render(Args, CmdArgs); Index: cfe/trunk/lib/Frontend/CompilerInvocation.cpp =================================================================== --- cfe/trunk/lib/Frontend/CompilerInvocation.cpp +++ cfe/trunk/lib/Frontend/CompilerInvocation.cpp @@ -713,6 +713,8 @@ Opts.VectorizeLoop = Args.hasArg(OPT_vectorize_loops); Opts.VectorizeSLP = Args.hasArg(OPT_vectorize_slp); + Opts.PreferVectorWidth = Args.getLastArgValue(OPT_mprefer_vector_width_EQ); + Opts.MainFileName = Args.getLastArgValue(OPT_main_file_name); Opts.VerifyModule = !Args.hasArg(OPT_disable_llvm_verifier); Index: cfe/trunk/test/CodeGen/attr-mprefer-vector-width.c =================================================================== --- cfe/trunk/test/CodeGen/attr-mprefer-vector-width.c +++ cfe/trunk/test/CodeGen/attr-mprefer-vector-width.c @@ -0,0 +1,14 @@ +// RUN: %clang_cc1 -mprefer-vector-width=128 -emit-llvm %s -o - | FileCheck %s --check-prefix=CHECK128 +// RUN: %clang_cc1 -mprefer-vector-width=256 -emit-llvm %s -o - | FileCheck %s --check-prefix=CHECK256 +// RUN: %clang_cc1 -mprefer-vector-width=none -emit-llvm %s -o - | FileCheck %s --check-prefix=CHECKNONE + +int baz(int a) { return 4; } + +// CHECK128: baz{{.*}} #0 +// CHECK128: #0 = {{.*}}"prefer-vector-width"="128" + +// CHECK256: baz{{.*}} #0 +// CHECK256: #0 = {{.*}}"prefer-vector-width"="256" + +// CHECKNONE: baz{{.*}} #0 +// CHECKNONE-NOT: #0 = {{.*}}"prefer-vector-width"="none" Index: cfe/trunk/test/Driver/mprefer-vector-width.c =================================================================== --- cfe/trunk/test/Driver/mprefer-vector-width.c +++ cfe/trunk/test/Driver/mprefer-vector-width.c @@ -0,0 +1,24 @@ +//// +//// Verify that valid options for the -mprefer-vector-width flag are passed through and invalid options cause an error. +//// + +//// If there are no options, convert to 'all'. + +// RUN: %clang -### -S %s -mprefer-vector-width=none 2>&1 | FileCheck --check-prefix=WIDTHNONE %s +// WIDTHNONE: "-mprefer-vector-width=none" + +//// Check options that cover all types. + +// RUN: %clang -### -S %s -mprefer-vector-width=128 2>&1 | FileCheck --check-prefix=WIDTH128 %s +// WIDTH128: "-mprefer-vector-width=128" + +//// Check invalid parameters. + +// RUN: %clang -### -S %s -mprefer-vector-width=one 2>&1 | FileCheck --check-prefix=WIDTHONE %s +// WIDTHONE: invalid value 'one' in 'mprefer-vector-width=' + +// RUN: %clang -### -S %s -mprefer-vector-width=128.5 2>&1 | FileCheck --check-prefix=WIDTH128p5 %s +// WIDTH128p5: invalid value '128.5' in 'mprefer-vector-width=' + +// RUN: %clang -### -S %s -mprefer-vector-width=-128 2>&1 | FileCheck --check-prefix=WIDTHNEG128 %s +// WIDTHNEG128: invalid value '-128' in 'mprefer-vector-width='