Completely re-work how the Clang driver interprets PIC and PIE options.
authorChandler Carruth <chandlerc@gmail.com>
Mon, 19 Nov 2012 03:52:03 +0000 (03:52 +0000)
committerChandler Carruth <chandlerc@gmail.com>
Mon, 19 Nov 2012 03:52:03 +0000 (03:52 +0000)
commit76a943be7beef5284d42ccd59a1e1f121ba3a8a9
tree52bcb47ac3528b074711701a39a09eb20c10fde0
parentd6f93cbe7ce63f6b7e9d332228f93b75f00e24f1
Completely re-work how the Clang driver interprets PIC and PIE options.

There were numerous issues here that were all entangled, and so I've
tried to do a general simplification of the logic.
1) The logic was mimicing actual GCC bugs, rather than "features". These
   have been fixed in trunk GCC, and this fixes Clang as well. Notably,
   the logic was always intended to be last-match-wins like any other
   flag.
2) The logic for handling '-mdynamic-no-pic' was preposterously unclear.
   It also allowed the use of this flag on non-Darwin platforms where it
   has no actual meaning. Now this option is handled directly based on
   tests of how llvm-gcc behaves, and it is only supported on Darwin.
3) The APIs for the Driver's ToolChains had the implementation ugliness
   of dynamic-no-pic leaking through them. They also had the
   implementation details of the LLVM relocation model flag names
   leaking through.
4) The actual results of passing these flags was incorrect on Darwin in
   many cases. For example, Darwin *always* uses PIC level 2 if it uses
   in PIC level, and Darwin *always* uses PIC on 64-bit regardless of
   the flags specified, including -fPIE. Darwin never compiles in PIE
   mode, but it can *link* in PIE mode.
5) Also, PIC was not always being enabled even when PIE was. This isn't
   a supported mode at all and may have caused some fallout in builds
   with complex PIC and PIE interactions.

The result is (I hope) cleaner and clearer for readers. I've also left
comments and tests about some of the truly strage behavior that is
observed on Darwin platforms. We have no real testing of Windows
platforms and PIC, but I don't have the tools handy to figure that out.
Hopefully others can beef up our testing here.

Unfortunately, I can't test this for every platform. =/ If folks have
dependencies on these flags that aren't covered by tests, they may
break. I've audited and ensured that all the changes in behavior of the
existing tests are intentional and good. In particular I've tried to
make sure the Darwin behavior (which is more suprising than the Linux
behavior) also matches that of 'gcc' on my mac.

llvm-svn: 168297
clang/include/clang/Basic/DiagnosticDriverKinds.td
clang/include/clang/Driver/ToolChain.h
clang/lib/Driver/ToolChains.cpp
clang/lib/Driver/ToolChains.h
clang/lib/Driver/Tools.cpp
clang/lib/Driver/WindowsToolChain.cpp
clang/test/Driver/pic.c