summaryrefslogtreecommitdiff
path: root/tools/libclang
diff options
context:
space:
mode:
authorDavid Majnemer <david.majnemer@gmail.com>2014-06-25 08:15:07 +0000
committerDavid Majnemer <david.majnemer@gmail.com>2014-06-25 08:15:07 +0000
commitab6dc444704d6f49ebc9ed60cc9fec0ec034b384 (patch)
tree4694247893b5188579763cd59234fcf5fe657f8e /tools/libclang
parent9f074fb6303750e5405d0192115cc53aeca3e262 (diff)
downloadclang-ab6dc444704d6f49ebc9ed60cc9fec0ec034b384.tar.gz
clang-ab6dc444704d6f49ebc9ed60cc9fec0ec034b384.tar.bz2
clang-ab6dc444704d6f49ebc9ed60cc9fec0ec034b384.tar.xz
AST: Initialization with dllimport functions in C
The C++ language requires that the address of a function be the same across all translation units. To make __declspec(dllimport) useful, this means that a dllimported function must also obey this rule. MSVC implements this by dynamically querying the import address table located in the linked executable. This means that the address of such a function in C++ is not constant (which violates other rules). However, the C language has no notion of ODR nor does it permit dynamic initialization whatsoever. This requires implementations to _not_ dynamically query the import address table and instead utilize a wrapper function that will be synthesized by the linker which will eventually query the import address table. The effect this has is, to say the least, perplexing. Consider the following C program: __declspec(dllimport) void f(void); typedef void (*fp)(void); static const fp var = &f; const fp fun() { return &f; } int main() { return fun() == var; } MSVC will statically initialize "var" with the address of the wrapper function and "fun" returns the address of the actual imported function. This means that "main" will return false! Note that LLVM's optimizers are strong enough to figure out that "main" should return true. However, this result is dependent on having optimizations enabled! N.B. This change also permits the usage of dllimport declarators inside of template arguments; they are sufficiently constant for such a purpose. Add tests to make sure we don't regress here. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@211677 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'tools/libclang')
0 files changed, 0 insertions, 0 deletions