1 //===-- ModuleUtils.cpp - Functions to manipulate Modules -----------------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This family of functions perform manipulations on Modules. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #include "llvm/Transforms/Utils/ModuleUtils.h" 15 #include "llvm/ADT/SmallPtrSet.h" 16 #include "llvm/IR/DerivedTypes.h" 17 #include "llvm/IR/Function.h" 18 #include "llvm/IR/IRBuilder.h" 19 #include "llvm/IR/Module.h" 20 21 using namespace llvm; 22 23 static void appendToGlobalArray(const char *Array, 24 Module &M, Function *F, int Priority) { 25 IRBuilder<> IRB(M.getContext()); 26 FunctionType *FnTy = FunctionType::get(IRB.getVoidTy(), false); 27 28 // Get the current set of static global constructors and add the new ctor 29 // to the list. 30 SmallVector<Constant *, 16> CurrentCtors; 31 StructType *EltTy; 32 if (GlobalVariable *GVCtor = M.getNamedGlobal(Array)) { 33 // If there is a global_ctors array, use the existing struct type, which can 34 // have 2 or 3 fields. 35 ArrayType *ATy = cast<ArrayType>(GVCtor->getType()->getElementType()); 36 EltTy = cast<StructType>(ATy->getElementType()); 37 if (Constant *Init = GVCtor->getInitializer()) { 38 unsigned n = Init->getNumOperands(); 39 CurrentCtors.reserve(n + 1); 40 for (unsigned i = 0; i != n; ++i) 41 CurrentCtors.push_back(cast<Constant>(Init->getOperand(i))); 42 } 43 GVCtor->eraseFromParent(); 44 } else { 45 // Use a simple two-field struct if there isn't one already. 46 EltTy = StructType::get(IRB.getInt32Ty(), PointerType::getUnqual(FnTy), 47 nullptr); 48 } 49 50 // Build a 2 or 3 field global_ctor entry. We don't take a comdat key. 51 Constant *CSVals[3]; 52 CSVals[0] = IRB.getInt32(Priority); 53 CSVals[1] = F; 54 // FIXME: Drop support for the two element form in LLVM 4.0. 55 if (EltTy->getNumElements() >= 3) 56 CSVals[2] = llvm::Constant::getNullValue(IRB.getInt8PtrTy()); 57 Constant *RuntimeCtorInit = 58 ConstantStruct::get(EltTy, makeArrayRef(CSVals, EltTy->getNumElements())); 59 60 CurrentCtors.push_back(RuntimeCtorInit); 61 62 // Create a new initializer. 63 ArrayType *AT = ArrayType::get(EltTy, CurrentCtors.size()); 64 Constant *NewInit = ConstantArray::get(AT, CurrentCtors); 65 66 // Create the new global variable and replace all uses of 67 // the old global variable with the new one. 68 (void)new GlobalVariable(M, NewInit->getType(), false, 69 GlobalValue::AppendingLinkage, NewInit, Array); 70 } 71 72 void llvm::appendToGlobalCtors(Module &M, Function *F, int Priority) { 73 appendToGlobalArray("llvm.global_ctors", M, F, Priority); 74 } 75 76 void llvm::appendToGlobalDtors(Module &M, Function *F, int Priority) { 77 appendToGlobalArray("llvm.global_dtors", M, F, Priority); 78 } 79 80 GlobalVariable * 81 llvm::collectUsedGlobalVariables(Module &M, SmallPtrSet<GlobalValue *, 8> &Set, 82 bool CompilerUsed) { 83 const char *Name = CompilerUsed ? "llvm.compiler.used" : "llvm.used"; 84 GlobalVariable *GV = M.getGlobalVariable(Name); 85 if (!GV || !GV->hasInitializer()) 86 return GV; 87 88 const ConstantArray *Init = cast<ConstantArray>(GV->getInitializer()); 89 for (unsigned I = 0, E = Init->getNumOperands(); I != E; ++I) { 90 Value *Op = Init->getOperand(I); 91 GlobalValue *G = cast<GlobalValue>(Op->stripPointerCastsNoFollowAliases()); 92 Set.insert(G); 93 } 94 return GV; 95 } 96