X86-Windows: Emit an undefined global __fltused symbol when targeting Windows

if any floating point arguments are passed to an external function.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@116665 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Michael J. Spencer 2010-10-16 08:25:41 +00:00
parent e70c526d59
commit 84ac4d5a2a
5 changed files with 60 additions and 2 deletions

View File

@ -157,6 +157,11 @@ class MachineModuleInfo : public ImmutablePass {
/// in this module.
bool DbgInfoAvailable;
/// True if this module calls an external function with floating point
/// arguments. This is used to emit an undefined reference to fltused on
/// Windows targets.
bool CallsExternalFunctionWithFloatingPointArguments;
public:
static char ID; // Pass identification, replacement for typeid
@ -211,7 +216,15 @@ public:
bool callsUnwindInit() const { return CallsUnwindInit; }
void setCallsUnwindInit(bool b) { CallsUnwindInit = b; }
bool callsExternalFunctionWithFloatingPointArguments() const {
return CallsExternalFunctionWithFloatingPointArguments;
}
void setCallsExternalFunctionWithFloatingPointArguments(bool b) {
CallsExternalFunctionWithFloatingPointArguments = b;
}
/// getFrameMoves - Returns a reference to a list of moves done in the current
/// function's prologue. Used to construct frame maps for debug and exception
/// handling comsumers.

View File

@ -256,7 +256,8 @@ void MMIAddrLabelMapCallbackPtr::allUsesReplacedWith(Value *V2) {
MachineModuleInfo::MachineModuleInfo(const MCAsmInfo &MAI)
: ImmutablePass(ID), Context(MAI),
ObjFileMMI(0),
CurCallSite(0), CallsEHReturn(0), CallsUnwindInit(0), DbgInfoAvailable(false){
CurCallSite(0), CallsEHReturn(0), CallsUnwindInit(0), DbgInfoAvailable(false),
CallsExternalFunctionWithFloatingPointArguments(false) {
// Always emit some info, by default "no personality" info.
Personalities.push_back(NULL);
AddrLabelSymbols = 0;

View File

@ -15,6 +15,7 @@
#include "SDNodeDbgValue.h"
#include "SelectionDAGBuilder.h"
#include "llvm/ADT/BitVector.h"
#include "llvm/ADT/PostOrderIterator.h"
#include "llvm/ADT/SmallSet.h"
#include "llvm/Analysis/AliasAnalysis.h"
#include "llvm/Analysis/ConstantFolding.h"
@ -5019,6 +5020,25 @@ void SelectionDAGBuilder::visitCall(const CallInst &I) {
}
}
// See if any floating point values are being passed to this external
// function. This is used to emit an undefined reference to fltused on
// Windows.
if (!F->hasLocalLinkage() && F->hasName()) {
MachineModuleInfo &MMI = DAG.getMachineFunction().getMMI();
for (unsigned i = 0, e = I.getNumArgOperands(); i != e &&
!MMI.callsExternalFunctionWithFloatingPointArguments(); ++i) {
const Type* T = I.getArgOperand(i)->getType();
for (po_iterator<const Type*> i = po_begin(T),
e = po_end(T);
i != e; ++i) {
if (i->isFloatingPointTy()) {
MMI.setCallsExternalFunctionWithFloatingPointArguments(true);
break;
}
}
}
}
// Check for well-known libc/libm calls. If the function is internal, it
// can't be a library call.
if (!F->hasLocalLinkage() && F->hasName()) {

View File

@ -580,6 +580,13 @@ void X86AsmPrinter::EmitEndOfAsmFile(Module &M) {
OutStreamer.EmitAssemblerFlag(MCAF_SubsectionsViaSymbols);
}
if (Subtarget->isTargetWindows()
&& !Subtarget->isTargetCygMing()
&& MMI->callsExternalFunctionWithFloatingPointArguments()) {
MCSymbol *S = MMI->getContext().GetOrCreateSymbol(StringRef("__fltused"));
OutStreamer.EmitSymbolAttribute(S, MCSA_Global);
}
if (Subtarget->isTargetCOFF()) {
X86COFFMachineModuleInfo &COFFMMI =
MMI->getObjFileInfo<X86COFFMachineModuleInfo>();

View File

@ -0,0 +1,17 @@
; The purpose of this test to to verify that the fltused symbol is emitted when
; any function is called with floating point arguments on Windows. And that it
; is not emitted otherwise.
; RUN: llc < %s -mtriple i686-pc-win32 | FileCheck %s
@.str = private constant [4 x i8] c"%f\0A\00"
define i32 @main() nounwind {
entry:
%call = tail call i32 (i8*, ...)* @printf(i8* getelementptr inbounds ([4 x i8]* @.str, i32 0, i32 0), double 1.000000e+000) nounwind
ret i32 0
}
declare i32 @printf(i8* nocapture, ...) nounwind
; CHECK: .globl __fltused