Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 7 additions & 4 deletions clang/include/clang/Driver/Options.td
Original file line number Diff line number Diff line change
Expand Up @@ -3454,7 +3454,8 @@ def fno_strict_aliasing : Flag<["-"], "fno-strict-aliasing">, Group<f_Group>,
def fstruct_path_tbaa : Flag<["-"], "fstruct-path-tbaa">, Group<f_Group>;
def fno_struct_path_tbaa : Flag<["-"], "fno-struct-path-tbaa">, Group<f_Group>;
def fno_strict_enums : Flag<["-"], "fno-strict-enums">, Group<f_Group>;
def fno_strict_overflow : Flag<["-"], "fno-strict-overflow">, Group<f_Group>;
def fno_strict_overflow : Flag<["-"], "fno-strict-overflow">, Group<f_Group>,
Visibility<[ClangOption, FlangOption]>;
def fno_pointer_tbaa : Flag<["-"], "fno-pointer-tbaa">, Group<f_Group>;
def fno_temp_file : Flag<["-"], "fno-temp-file">, Group<f_Group>,
Visibility<[ClangOption, CC1Option, CLOption, DXCOption]>, HelpText<
Expand All @@ -3470,7 +3471,8 @@ def fno_verbose_asm : Flag<["-"], "fno-verbose-asm">, Group<f_Group>,
Visibility<[ClangOption, CC1Option]>,
MarshallingInfoNegativeFlag<CodeGenOpts<"AsmVerbose">>;
def fno_working_directory : Flag<["-"], "fno-working-directory">, Group<f_Group>;
def fno_wrapv : Flag<["-"], "fno-wrapv">, Group<f_Group>;
def fno_wrapv : Flag<["-"], "fno-wrapv">, Group<f_Group>,
Visibility<[ClangOption, FlangOption]>;
def fobjc_arc : Flag<["-"], "fobjc-arc">, Group<f_Group>,
Visibility<[ClangOption, CC1Option]>,
HelpText<"Synthesize retain and release calls for Objective-C pointers">;
Expand Down Expand Up @@ -3966,7 +3968,8 @@ defm strict_vtable_pointers : BoolFOption<"strict-vtable-pointers",
"Enable optimizations based on the strict rules for"
" overwriting polymorphic C++ objects">,
NegFlag<SetFalse>>;
def fstrict_overflow : Flag<["-"], "fstrict-overflow">, Group<f_Group>;
def fstrict_overflow : Flag<["-"], "fstrict-overflow">, Group<f_Group>,
Visibility<[ClangOption, FlangOption]>;
def fpointer_tbaa : Flag<["-"], "fpointer-tbaa">, Group<f_Group>;
def fdriver_only : Flag<["-"], "fdriver-only">, Flags<[NoXarchOption]>,
Visibility<[ClangOption, CLOption, DXCOption]>,
Expand Down Expand Up @@ -4235,7 +4238,7 @@ defm virtual_function_elimination : BoolFOption<"virtual-function-elimination",
NegFlag<SetFalse>, BothFlags<[], [ClangOption, CLOption]>>;

def fwrapv : Flag<["-"], "fwrapv">, Group<f_Group>,
Visibility<[ClangOption, CC1Option]>,
Visibility<[ClangOption, CC1Option, FlangOption, FC1Option]>,
HelpText<"Treat signed integer overflow as two's complement">;
def fwritable_strings : Flag<["-"], "fwritable-strings">, Group<f_Group>,
Visibility<[ClangOption, CC1Option]>,
Expand Down
13 changes: 3 additions & 10 deletions clang/lib/Driver/ToolChains/Clang.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6914,16 +6914,9 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA,

Args.AddLastArg(CmdArgs, options::OPT_ftrap_function_EQ);

// -fno-strict-overflow implies -fwrapv if it isn't disabled, but
// -fstrict-overflow won't turn off an explicitly enabled -fwrapv.
if (Arg *A = Args.getLastArg(options::OPT_fwrapv, options::OPT_fno_wrapv)) {
if (A->getOption().matches(options::OPT_fwrapv))
CmdArgs.push_back("-fwrapv");
} else if (Arg *A = Args.getLastArg(options::OPT_fstrict_overflow,
options::OPT_fno_strict_overflow)) {
if (A->getOption().matches(options::OPT_fno_strict_overflow))
CmdArgs.push_back("-fwrapv");
}
// Handle -f[no-]wrapv and -f[no-]strict-overflow, which are used by both
// clang and flang.
renderCommonIntegerOverflowOptions(Args, CmdArgs);

Args.AddLastArg(CmdArgs, options::OPT_ffinite_loops,
options::OPT_fno_finite_loops);
Expand Down
14 changes: 14 additions & 0 deletions clang/lib/Driver/ToolChains/CommonArgs.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3048,3 +3048,17 @@ bool tools::shouldRecordCommandLine(const ToolChain &TC,

return FRecordCommandLine || TC.UseDwarfDebugFlags() || GRecordCommandLine;
}

void tools::renderCommonIntegerOverflowOptions(const ArgList &Args,
ArgStringList &CmdArgs) {
// -fno-strict-overflow implies -fwrapv if it isn't disabled, but
// -fstrict-overflow won't turn off an explicitly enabled -fwrapv.
if (Arg *A = Args.getLastArg(options::OPT_fwrapv, options::OPT_fno_wrapv)) {
if (A->getOption().matches(options::OPT_fwrapv))
CmdArgs.push_back("-fwrapv");
} else if (Arg *A = Args.getLastArg(options::OPT_fstrict_overflow,
options::OPT_fno_strict_overflow)) {
if (A->getOption().matches(options::OPT_fno_strict_overflow))
CmdArgs.push_back("-fwrapv");
}
}
3 changes: 3 additions & 0 deletions clang/lib/Driver/ToolChains/CommonArgs.h
Original file line number Diff line number Diff line change
Expand Up @@ -262,6 +262,9 @@ bool shouldRecordCommandLine(const ToolChain &TC,
bool &FRecordCommandLine,
bool &GRecordCommandLine);

void renderCommonIntegerOverflowOptions(const llvm::opt::ArgList &Args,
llvm::opt::ArgStringList &CmdArgs);

} // end namespace tools
} // end namespace driver
} // end namespace clang
Expand Down
2 changes: 2 additions & 0 deletions clang/lib/Driver/ToolChains/Flang.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -869,6 +869,8 @@ void Flang::ConstructJob(Compilation &C, const JobAction &JA,
}
}

renderCommonIntegerOverflowOptions(Args, CmdArgs);

assert((Output.isFilename() || Output.isNothing()) && "Invalid output.");
if (Output.isFilename()) {
CmdArgs.push_back("-o");
Expand Down
2 changes: 2 additions & 0 deletions flang/include/flang/Common/LangOptions.def
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@ LANGOPT(Name, Bits, Default)
#endif

ENUM_LANGOPT(FPContractMode, FPModeKind, 2, FPM_Fast) ///< FP Contract Mode (off/fast)
/// signed integer overflow handling
ENUM_LANGOPT(SignedOverflowBehavior, SignedOverflowBehaviorTy, 1, SOB_Undefined)

/// Indicate a build without the standard GPU libraries.
LANGOPT(NoGPULib , 1, false)
Expand Down
8 changes: 8 additions & 0 deletions flang/include/flang/Common/LangOptions.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,14 @@ namespace Fortran::common {
class LangOptionsBase {

public:
enum SignedOverflowBehaviorTy {
// -fno-wrapv (default behavior in Flang)
SOB_Undefined,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

unused? Not sure that this definition is useful

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is used as the default value of a LangOption SignedOverflowBehavior. If the behavior is not defined, nsw could be added to some operations such as add.
FWIW, this implementation is simliar to that of Clang.


// -fwrapv
SOB_Defined,
};

enum FPModeKind {
// Do not fuse FP ops
FPM_Off,
Expand Down
5 changes: 2 additions & 3 deletions flang/include/flang/Lower/LoweringOptions.def
Original file line number Diff line number Diff line change
Expand Up @@ -35,9 +35,8 @@ ENUM_LOWERINGOPT(NoPPCNativeVecElemOrder, unsigned, 1, 0)
ENUM_LOWERINGOPT(Underscoring, unsigned, 1, 1)

/// If true, assume the behavior of integer overflow is defined
/// (i.e. wraps around as two's complement). On by default.
/// TODO: make the default off
ENUM_LOWERINGOPT(IntegerWrapAround, unsigned, 1, 1)
/// (i.e. wraps around as two's complement). Off by default.
ENUM_LOWERINGOPT(IntegerWrapAround, unsigned, 1, 0)

/// If true, add nsw flags to loop variable increments.
/// Off by default.
Expand Down
36 changes: 33 additions & 3 deletions flang/lib/Frontend/CompilerInvocation.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1115,6 +1115,24 @@ static bool parseOpenMPArgs(CompilerInvocation &res, llvm::opt::ArgList &args,
return diags.getNumErrors() == numErrorsBefore;
}

/// Parses signed integer overflow options and populates the
/// CompilerInvocation accordingly.
/// Returns false if new errors are generated.
///
/// \param [out] invoc Stores the processed arguments
/// \param [in] args The compiler invocation arguments to parse
/// \param [out] diags DiagnosticsEngine to report erros with
static bool parseIntegerOverflowArgs(CompilerInvocation &invoc,
llvm::opt::ArgList &args,
clang::DiagnosticsEngine &diags) {
Fortran::common::LangOptions &opts = invoc.getLangOpts();

if (args.getLastArg(clang::driver::options::OPT_fwrapv))
opts.setSignedOverflowBehavior(Fortran::common::LangOptions::SOB_Defined);

return true;
}

/// Parses all floating point related arguments and populates the
/// CompilerInvocation accordingly.
/// Returns false if new errors are generated.
Expand Down Expand Up @@ -1255,6 +1273,18 @@ static bool parseLinkerOptionsArgs(CompilerInvocation &invoc,
return true;
}

static bool parseLangOptionsArgs(CompilerInvocation &invoc,
llvm::opt::ArgList &args,
clang::DiagnosticsEngine &diags) {
bool success = true;

success &= parseIntegerOverflowArgs(invoc, args, diags);
success &= parseFloatingPointArgs(invoc, args, diags);
success &= parseVScaleArgs(invoc, args, diags);

return success;
}

bool CompilerInvocation::createFromArgs(
CompilerInvocation &invoc, llvm::ArrayRef<const char *> commandLineArgs,
clang::DiagnosticsEngine &diags, const char *argv0) {
Expand Down Expand Up @@ -1363,9 +1393,7 @@ bool CompilerInvocation::createFromArgs(
invoc.frontendOpts.mlirArgs =
args.getAllArgValues(clang::driver::options::OPT_mmlir);

success &= parseFloatingPointArgs(invoc, args, diags);

success &= parseVScaleArgs(invoc, args, diags);
success &= parseLangOptionsArgs(invoc, args, diags);

success &= parseLinkerOptionsArgs(invoc, args, diags);

Expand Down Expand Up @@ -1577,6 +1605,8 @@ void CompilerInvocation::setLoweringOptions() {
loweringOpts.setUnderscoring(codegenOpts.Underscoring);

const Fortran::common::LangOptions &langOptions = getLangOpts();
loweringOpts.setIntegerWrapAround(langOptions.getSignedOverflowBehavior() ==
Fortran::common::LangOptions::SOB_Defined);
Fortran::common::MathOptionsBase &mathOpts = loweringOpts.getMathOptions();
// TODO: when LangOptions are finalized, we can represent
// the math related options using Fortran::commmon::MathOptionsBase,
Expand Down
2 changes: 2 additions & 0 deletions flang/test/Driver/frontend-forwarding.f90
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
! RUN: -fno-signed-zeros \
! RUN: -fassociative-math \
! RUN: -freciprocal-math \
! RUN: -fno-strict-overflow \
! RUN: -fomit-frame-pointer \
! RUN: -fpass-plugin=Bye%pluginext \
! RUN: -fversion-loops-for-stride \
Expand Down Expand Up @@ -63,4 +64,5 @@
! CHECK: "-Rpass=inline"
! CHECK: "-mframe-pointer=none"
! CHECK: "-mllvm" "-print-before-all"
! CHECK: "-fwrapv"
! CHECK: "-save-temps=obj"
10 changes: 10 additions & 0 deletions flang/test/Driver/integer-overflow.f90
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
! Test for correct forwarding of integer overflow flags from the compiler driver
! to the frontend driver

! RUN: %flang -### -fno-strict-overflow %s 2>&1 | FileCheck %s --check-prefix=INDUCED
! RUN: %flang -### -fstrict-overflow %s 2>&1 | FileCheck %s
! RUN: %flang -### -fno-wrapv %s 2>&1 | FileCheck %s
! RUN: %flang -### -fno-wrapv -fno-strict-overflow %s 2>&1 | FileCheck %s

! CHECK-NOT: "-fno-wrapv"
! INDUCED: "-fwrapv"