Merge remote-tracking branch 'origin/master' into merge-2.064

Conflicts:
	gen/arrays.cpp
This commit is contained in:
Kai Nacke 2013-12-19 21:27:53 +01:00
commit c231ae0ad0
5 changed files with 76 additions and 69 deletions

View file

@ -7,6 +7,9 @@ if(MSVC)
set(LIBCONFIG_DLL OFF CACHE BOOL "Use libconfig++ DLL instead of static library")
endif()
include(CheckIncludeFile)
include(CheckLibraryExists)
#
# Locate LLVM.
#
@ -350,6 +353,35 @@ else()
add_definitions(-D__LITTLE_ENDIAN__)
endif()
#
# Check if libpthread is available.
# FIXME: Guard with LLVM_ENABLE_THREADS
#
if( NOT WIN32 OR CYGWIN )
check_include_file(pthread.h HAVE_PTHREAD_H)
check_library_exists(pthread pthread_create "" HAVE_LIBPTHREAD)
if(HAVE_LIBPTHREAD)
set(PTHREAD_LIBS -lpthread)
endif()
endif()
#
# Check if terminfo is available.
# FIXME: Guard with LLVM_ENABLE_TERMINFO
#
if( NOT WIN32 OR CYGWIN )
set(HAVE_TERMINFO 0)
foreach(library tinfo terminfo curses ncurses ncursesw)
string(TOUPPER ${library} library_suffix)
check_library_exists(${library} setupterm "" HAVE_TERMINFO_${library_suffix})
if(HAVE_TERMINFO_${library_suffix})
set(HAVE_TERMINFO 1)
set(TERMINFO_LIBS "${library}")
break()
endif()
endforeach()
endif()
#
# Set up the main ldc/ldc2 target.
#
@ -374,7 +406,7 @@ set_target_properties(
)
# LDFLAGS should actually be in target property LINK_FLAGS, but this works, and gets around linking problems
target_link_libraries(${LDC_LIB} ${LLVM_LIBRARIES} "${LLVM_LDFLAGS}")
target_link_libraries(${LDC_LIB} ${LLVM_LIBRARIES} ${PTHREAD_LIBS} ${TERMINFO_LIBS} "${LLVM_LDFLAGS}")
if(WIN32)
target_link_libraries(${LDC_LIB} imagehlp psapi)
elseif(${CMAKE_SYSTEM_NAME} MATCHES "Linux")
@ -394,7 +426,7 @@ set_target_properties(
COMPILE_FLAGS "${LLVM_CXXFLAGS} ${EXTRA_CXXFLAGS}"
LINK_FLAGS "${SANITIZE_LDFLAGS}"
)
target_link_libraries(${LDC_EXE} ${LDC_LIB} ${LIBCONFIG++_LIBRARY})
target_link_libraries(${LDC_EXE} ${LDC_LIB} ${LIBCONFIG++_LIBRARY} ${PTHREAD_LIBS} ${CMAKE_DL_LIBS} ${TERMINFO_LIBS})
if(MSVC)
# Add a post build event in Visual Studio to copy the config file into Debug/Release folder
add_custom_command(TARGET ${LDC_EXE} POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy ${PROJECT_BINARY_DIR}/bin/${LDC_EXE}.conf $<TARGET_FILE_DIR:${LDC_EXE}> COMMENT "Copy config file ${LDC_EXE}.conf")
@ -432,7 +464,7 @@ set_target_properties(
COMPILE_FLAGS "${TABLEGEN_CXXFLAGS} ${LDC_CXXFLAGS}"
LINK_FLAGS "${SANITIZE_LDFLAGS}"
)
target_link_libraries(gen_gccbuiltins ${LLVM_LIBRARIES} "${LLVM_LDFLAGS}")
target_link_libraries(gen_gccbuiltins ${LLVM_LIBRARIES} ${PTHREAD_LIBS} ${TERMINFO_LIBS} ${CMAKE_DL_LIBS} "${LLVM_LDFLAGS}")
if(${CMAKE_SYSTEM_NAME} MATCHES "Linux")
target_link_libraries(gen_gccbuiltins dl)
endif()
@ -463,7 +495,7 @@ set_target_properties(${LDMD_EXE} PROPERTIES
# use symbols from libdl, ..., so LLVM_LDFLAGS must come _after_ them in the
# command line. Maybe this could be improved using library groups, at least with
# GNU ld.
target_link_libraries(${LDMD_EXE} ${LLVM_LIBRARIES} "${LLVM_LDFLAGS}")
target_link_libraries(${LDMD_EXE} ${LLVM_LIBRARIES} ${PTHREAD_LIBS} ${TERMINFO_LIBS} ${CMAKE_DL_LIBS} "${LLVM_LDFLAGS}")
#
# Test and runtime targets. Note that enable_testing() is order-sensitive!

View file

@ -52,6 +52,9 @@ llvm::FunctionType* DtoFunctionType(Type* type, IrFuncTy &irFty, Type* thistype,
assert(f->next && "Encountered function type with invalid return type; "
"trying to codegen function ignored by the frontend?");
// Return cached type if available
if (irFty.funcType) return irFty.funcType;
TargetABI* abi = (f->linkage == LINKintrinsic ? TargetABI::getIntrinsic() : gABI);
// Tell the ABI we're resolving a new function type
abi->newFunctionType(f);
@ -285,11 +288,11 @@ llvm::FunctionType* DtoFunctionType(Type* type, IrFuncTy &irFty, Type* thistype,
std::reverse(argtypes.begin() + beg, argtypes.end());
}
LLFunctionType* functype = LLFunctionType::get(irFty.ret->ltype, argtypes, irFty.c_vararg);
irFty.funcType = LLFunctionType::get(irFty.ret->ltype, argtypes, irFty.c_vararg);
Logger::cout() << "Final function type: " << *functype << "\n";
Logger::cout() << "Final function type: " << *irFty.funcType << "\n";
return functype;
return irFty.funcType;
}
//////////////////////////////////////////////////////////////////////////////////////////

View file

@ -56,6 +56,10 @@
using namespace llvm;
#if LDC_LLVM_VER < 302
typedef TargetData DataLayout;
#endif
STATISTIC(NumGcToStack, "Number of calls promoted to constant-size allocas");
STATISTIC(NumToDynSize, "Number of calls promoted to dynamically-sized allocas");
STATISTIC(NumDeleted, "Number of GC calls deleted because the return value was unused");
@ -66,11 +70,7 @@ SizeLimit("dgc2stack-size-limit", cl::init(1024), cl::Hidden,
namespace {
struct Analysis {
#if LDC_LLVM_VER >= 302
DataLayout& TD;
#else
TargetData& TD;
#endif
DataLayout& DL;
const Module& M;
CallGraph* CG;
CallGraphNode* CGNode;
@ -151,7 +151,7 @@ namespace {
APInt Mask = APInt::getLowBitsSet(Bits, BitsLimit);
Mask.flipAllBits();
APInt KnownZero(Bits, 0), KnownOne(Bits, 0);
ComputeMaskedBits(Val, KnownZero, KnownOne, &A.TD);
ComputeMaskedBits(Val, KnownZero, KnownOne, &A.DL);
if ((KnownZero & Mask) != Mask)
return false;
@ -171,7 +171,7 @@ namespace {
Value* TypeInfo = CS.getArgument(TypeInfoArgNr);
Ty = A.getTypeFor(TypeInfo);
if (!Ty) return false;
return A.TD.getTypeAllocSize(Ty) < SizeLimit;
return A.DL.getTypeAllocSize(Ty) < SizeLimit;
}
};
@ -207,7 +207,7 @@ namespace {
// (set bits) inference algorithm is rather limited, this is
// useful for experimenting.
if (SizeLimit > 0) {
uint64_t ElemSize = A.TD.getTypeAllocSize(Ty);
uint64_t ElemSize = A.DL.getTypeAllocSize(Ty);
if (!isKnownLessThan(arrSize, SizeLimit / ElemSize, A))
return false;
}
@ -237,7 +237,7 @@ namespace {
if (Initialized) {
// For now, only zero-init is supported.
uint64_t size = A.TD.getTypeStoreSize(Ty);
uint64_t size = A.DL.getTypeStoreSize(Ty);
Value* TypeSize = ConstantInt::get(arrSize->getType(), size);
// Use the original B to put initialization at the
// allocation site.
@ -295,7 +295,7 @@ namespace {
return false;
Ty =node->getOperand(CD_BodyType)->getType();
return A.TD.getTypeAllocSize(Ty) < SizeLimit;
return A.DL.getTypeAllocSize(Ty) < SizeLimit;
}
// The default promote() should be fine.
@ -390,11 +390,7 @@ namespace {
bool runOnFunction(Function &F);
virtual void getAnalysisUsage(AnalysisUsage &AU) const {
#if LDC_LLVM_VER >= 302
AU.addRequired<DataLayout>();
#else
AU.addRequired<TargetData>();
#endif
AU.addRequired<DominatorTree>();
#if LDC_LLVM_VER >= 305
@ -458,11 +454,7 @@ static bool isSafeToStackAllocate(Instruction* Alloc, Value* V, DominatorTree& D
bool GarbageCollect2Stack::runOnFunction(Function &F) {
DEBUG(errs() << "\nRunning -dgc2stack on function " << F.getName() << '\n');
#if LDC_LLVM_VER >= 302
DataLayout& TD = getAnalysis<DataLayout>();
#else
TargetData& TD = getAnalysis<TargetData>();
#endif
DataLayout& DL = getAnalysis<DataLayout>();
DominatorTree& DT = getAnalysis<DominatorTree>();
#if LDC_LLVM_VER >= 305
CallGraphWrapperPass* CGPass = getAnalysisIfAvailable<CallGraphWrapperPass>();
@ -472,7 +464,7 @@ bool GarbageCollect2Stack::runOnFunction(Function &F) {
#endif
CallGraphNode* CGNode = CG ? (*CG)[&F] : NULL;
Analysis A = { TD, *M, CG, CGNode };
Analysis A = { DL, *M, CG, CGNode };
BasicBlock& Entry = F.getEntryBlock();

View file

@ -45,6 +45,10 @@
using namespace llvm;
#if LDC_LLVM_VER < 302
typedef TargetData DataLayout;
#endif
STATISTIC(NumSimplified, "Number of runtime calls simplified");
STATISTIC(NumDeleted, "Number of runtime calls deleted");
@ -59,11 +63,7 @@ namespace {
protected:
Function *Caller;
bool* Changed;
#if LDC_LLVM_VER >= 302
const DataLayout *TD;
#else
const TargetData *TD;
#endif
const DataLayout *DL;
AliasAnalysis *AA;
LLVMContext *Context;
@ -85,16 +85,11 @@ namespace {
/// delete CI.
virtual Value *CallOptimizer(Function *Callee, CallInst *CI, IRBuilder<> &B)=0;
#if LDC_LLVM_VER >= 302
Value *OptimizeCall(CallInst *CI, bool& Changed, const DataLayout &TD,
Value *OptimizeCall(CallInst *CI, bool& Changed, const DataLayout &DL,
AliasAnalysis& AA, IRBuilder<> &B) {
#else
Value *OptimizeCall(CallInst *CI, bool& Changed, const TargetData &TD,
AliasAnalysis& AA, IRBuilder<> &B) {
#endif
Caller = CI->getParent()->getParent();
this->Changed = &Changed;
this->TD = &TD;
this->DL = &DL;
this->AA = &AA;
if (CI->getCalledFunction())
Context = &CI->getCalledFunction()->getContext();
@ -112,14 +107,7 @@ Value *LibCallOptimization::CastToCStr(Value *V, IRBuilder<> &B) {
/// expects that the size has type 'intptr_t' and Dst/Src are pointers.
Value *LibCallOptimization::EmitMemCpy(Value *Dst, Value *Src, Value *Len,
unsigned Align, IRBuilder<> &B) {
Module *M = Caller->getParent();
Type* intTy = Len->getType();
Type *VoidPtrTy = PointerType::getUnqual(B.getInt8Ty());
Type *Tys[3] ={VoidPtrTy, VoidPtrTy, intTy};
Value *MemCpy = Intrinsic::getDeclaration(M, Intrinsic::memcpy, llvm::makeArrayRef(Tys, 3));
return B.CreateCall5(MemCpy, CastToCStr(Dst, B), CastToCStr(Src, B), Len,
ConstantInt::get(B.getInt32Ty(), Align), B.getFalse());
return B.CreateMemCpy(CastToCStr(Dst, B), CastToCStr(Src, B), Len, Align, false);
}
//===----------------------------------------------------------------------===//
@ -312,18 +300,10 @@ namespace {
void InitOptimizations();
bool runOnFunction(Function &F);
#if LDC_LLVM_VER >= 302
bool runOnce(Function &F, const DataLayout& DL, AliasAnalysis& AA);
#else
bool runOnce(Function &F, const TargetData& TD, AliasAnalysis& AA);
#endif
virtual void getAnalysisUsage(AnalysisUsage &AU) const {
#if LDC_LLVM_VER >= 302
AU.addRequired<DataLayout>();
#else
AU.addRequired<TargetData>();
#endif
AU.addRequired<AliasAnalysis>();
}
};
@ -373,11 +353,7 @@ bool SimplifyDRuntimeCalls::runOnFunction(Function &F) {
if (Optimizations.empty())
InitOptimizations();
#if LDC_LLVM_VER >= 302
const DataLayout &TD = getAnalysis<DataLayout>();
#else
const TargetData &TD = getAnalysis<TargetData>();
#endif
const DataLayout &DL = getAnalysis<DataLayout>();
AliasAnalysis &AA = getAnalysis<AliasAnalysis>();
// Iterate to catch opportunities opened up by other optimizations,
@ -388,18 +364,14 @@ bool SimplifyDRuntimeCalls::runOnFunction(Function &F) {
bool EverChanged = false;
bool Changed;
do {
Changed = runOnce(F, TD, AA);
Changed = runOnce(F, DL, AA);
EverChanged |= Changed;
} while (Changed);
return EverChanged;
}
#if LDC_LLVM_VER >= 302
bool SimplifyDRuntimeCalls::runOnce(Function &F, const DataLayout& TD, AliasAnalysis& AA) {
#else
bool SimplifyDRuntimeCalls::runOnce(Function &F, const TargetData& TD, AliasAnalysis& AA) {
#endif
bool SimplifyDRuntimeCalls::runOnce(Function &F, const DataLayout& DL, AliasAnalysis& AA) {
IRBuilder<> Builder(F.getContext());
bool Changed = false;
@ -426,7 +398,7 @@ bool SimplifyDRuntimeCalls::runOnce(Function &F, const TargetData& TD, AliasAnal
Builder.SetInsertPoint(BB, I);
// Try to optimize this call.
Value *Result = OMI->second->OptimizeCall(CI, Changed, TD, AA, Builder);
Value *Result = OMI->second->OptimizeCall(CI, Changed, DL, AA, Builder);
if (Result == 0) continue;
DEBUG(errs() << "SimplifyDRuntimeCalls simplified: " << *CI;

View file

@ -33,6 +33,7 @@ namespace llvm {
class Value;
class Instruction;
class Function;
class FunctionType;
}
// represents a function type argument
@ -87,6 +88,9 @@ struct IrFuncTyArg
// represents a function type
struct IrFuncTy
{
// The final LLVM type
llvm::FunctionType* funcType;
// return value
IrFuncTyArg* ret;
@ -111,7 +115,8 @@ struct IrFuncTy
bool reverseParams;
IrFuncTy()
: ret(NULL),
: funcType(0),
ret(NULL),
arg_sret(NULL),
arg_this(NULL),
arg_nest(NULL),
@ -126,7 +131,8 @@ struct IrFuncTy
// Copy constructor and operator= seems to be required for MSC
IrFuncTy(const IrFuncTy& rhs)
: ret(rhs.ret),
: funcType(ths.funcType),
ret(rhs.ret),
args(IrFuncTy::ArgList(rhs.args)),
arg_sret(rhs.arg_sret),
arg_this(rhs.arg_this),
@ -139,6 +145,7 @@ struct IrFuncTy
IrFuncTy& operator=(const IrFuncTy& rhs)
{
funcType = rhs.funcType;
ret = rhs.ret;
args = IrFuncTy::ArgList(rhs.args);
arg_sret = rhs.arg_sret;
@ -153,6 +160,7 @@ struct IrFuncTy
#endif
void reset() {
funcType = 0;
ret = NULL;
arg_sret = arg_this = arg_nest = arg_arguments = arg_argptr = NULL;
#if defined(_MSC_VER)