ccc: Pass -f[no-]math-errno to clang.


git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@64709 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/tools/ccc/ccclib/Arguments.py b/tools/ccc/ccclib/Arguments.py
index 5d20fea..6cda01b 100644
--- a/tools/ccc/ccclib/Arguments.py
+++ b/tools/ccc/ccclib/Arguments.py
@@ -364,9 +364,30 @@
                 arg.opt.matches(optionC)):
                 yield arg
 
-    def getLastArg(self, option):
-        return self.lastArgs.get(option)
+    def getLastArgAndPosition(self, option):
+        return self.lastArgs.get(option, (None,-1))
 
+    def getLastArg(self, option):
+        return self.getLastArgAndPosition(option)[0]
+
+    def hasFFlag(self, option, negativeOption, default):
+        """hasFFlag - Given an option and its corresponding negative
+        option, return True if the option is present, False if the
+        negation is present, and default if neither option is
+        given. If both the option and its negation are present, the
+        last one wins.
+        """
+        arg,argPos = self.getLastArgAndPosition(option)
+        neg,negPos = self.getLastArgAndPosition(negativeOption)
+        if arg and neg:
+            return negPos < argPos
+        elif arg:
+            return True
+        elif neg:
+            return False
+        else:
+            return default
+            
     def getInputString(self, index, offset=0):
         # Source 0 is argv.
         if index.sourceId == 0:
@@ -457,9 +478,9 @@
         opt = arg.opt
         if opt.alias:
             opt = opt.alias
-        self.lastArgs[opt] = arg
+        self.lastArgs[opt] = (arg, len(self.args) - 1)
         if opt.group is not None:
-            self.lastArgs[opt.group] = arg
+            self.lastArgs[opt.group] = (arg, len(self.args) - 1)
 
     # Forwarding methods.
     #
@@ -793,6 +814,8 @@
         self.f_indirectVirtualCallsOption = self.addOption(FlagOption('-findirect-virtual-calls', self.fGroup))
         self.f_laxVectorConversionsOption = self.addOption(FlagOption('-flax-vector-conversions', self.Clang_fGroup))
         self.f_limitedPrecisionOption = self.addOption(JoinedOption('-flimited-precision=', self.fGroup))
+        self.f_mathErrnoOption = self.addOption(FlagOption('-fmath-errno', self.fGroup))
+        self.f_noMathErrnoOption = self.addOption(FlagOption('-fno-math-errno', self.fGroup))
         self.f_msExtensionsOption = self.addOption(FlagOption('-fms-extensions', self.Clang_fGroup))
         self.f_mudflapOption = self.addOption(FlagOption('-fmudflap', self.fGroup))
         self.f_mudflapthOption = self.addOption(FlagOption('-fmudflapth', self.fGroup))
diff --git a/tools/ccc/ccclib/ToolChain.py b/tools/ccc/ccclib/ToolChain.py
index 2fd500c..f2f22a0 100644
--- a/tools/ccc/ccclib/ToolChain.py
+++ b/tools/ccc/ccclib/ToolChain.py
@@ -76,6 +76,9 @@
 
         return True
         
+    def isMathErrnoDefault(self):
+        return True
+
 class Darwin_X86_ToolChain(ToolChain):
     def __init__(self, driver, darwinVersion, gccVersion, archName):
         super(Darwin_X86_ToolChain, self).__init__(driver)
@@ -224,6 +227,9 @@
 
         return al
 
+    def isMathErrnoDefault(self):
+        return False
+
 class Generic_GCC_ToolChain(ToolChain):
     """Generic_GCC_ToolChain - A tool chain using the 'gcc' command to
     perform all subcommands; this relies on gcc translating the
diff --git a/tools/ccc/ccclib/Tools.py b/tools/ccc/ccclib/Tools.py
index d3ba30e..5da2de2 100644
--- a/tools/ccc/ccclib/Tools.py
+++ b/tools/ccc/ccclib/Tools.py
@@ -280,6 +280,13 @@
             if arglist.getLastArg(arglist.parser.f_unwindTablesOption):
                 cmd_args.append('--unwind-tables')
 
+            if arglist.hasFFlag(arglist.parser.f_mathErrnoOption,
+                                arglist.parser.f_noMathErrnoOption,
+                                self.toolChain.isMathErrnoDefault()):
+                cmd_args.append('--fmath-errno=1')
+            else:
+                cmd_args.append('--fmath-errno=0')
+
             arg = arglist.getLastArg(arglist.parser.f_limitedPrecisionOption)
             if arg:
                 cmd_args.append('--limit-float-precision')
diff --git a/tools/ccc/test/ccc/math-errno.c b/tools/ccc/test/ccc/math-errno.c
new file mode 100644
index 0000000..4f440a3
--- /dev/null
+++ b/tools/ccc/test/ccc/math-errno.c
@@ -0,0 +1,5 @@
+// RUN: xcc -ccc-host-system unknown -### %s -S 2>&1 | grep -- "--fmath-errno=1" | count 1 &&
+// RUN: xcc -ccc-host-system unknown -### %s -S -fno-math-errno 2>&1 | grep -- "--fmath-errno=0" | count 1 &&
+// RUN: xcc -ccc-host-system unknown -### %s -S -fmath-errno -fno-math-errno 2>&1 | grep -- "--fmath-errno=0" | count 1 &&
+// RUN: xcc -ccc-host-bits 32 -ccc-host-machine i386 -ccc-host-system darwin -ccc-host-release 10.5.0 -### %s -S 2>&1 | grep -- "--fmath-errno=0" | count 1 &&
+// RUN: xcc -ccc-host-bits 32 -ccc-host-machine i386 -ccc-host-system darwin -ccc-host-release 10.5.0 -### %s -S -fmath-errno 2>&1 | grep -- "--fmath-errno=1" | count 1