31#define DEBUG_TYPE "ppc-merge-strings"
33STATISTIC(NumPooledStrings,
"Number of Strings Pooled");
39 cl::desc(
"Maximum Number of Strings to Pool."));
43 cl::desc(
"Minimum number of string candidates before "
44 "pooling is considered."));
52 Align LHSAlign =
LHS->getAlign().valueOrOne();
53 Align RHSAlign =
RHS->getAlign().valueOrOne();
54 if (LHSAlign > RHSAlign)
56 else if (LHSAlign < RHSAlign)
69 dyn_cast<ConstantDataSequential>(ConstLHS);
74 dyn_cast<ConstantDataSequential>(ConstRHS);
80 return LHSSize < RHSSize;
104 std::vector<GlobalVariable *> MergeableStrings;
106 Type *PooledStructType;
108 void collectCandidateConstants(
Module &M);
109 bool mergeModuleStringPool(
Module &M);
111 unsigned ElementIndex);
121 if (isa<Instruction>(CurrentUser))
129 if (isa<GlobalValue>(CurrentUser))
133 if (!isa<Constant>(CurrentUser))
143void PPCMergeStringPool::collectCandidateConstants(
Module &M) {
152 AllUsedGlobals.
insert(UsedVCompiler.
begin(), UsedVCompiler.
end());
179 dyn_cast<ConstantDataSequential>(
Global.getInitializer());
189 if (!hasReplaceableUsers(
Global))
192 Align AlignOfGlobal =
Global.getAlign().valueOrOne();
210 MergeableStrings.push_back(&
Global);
211 if (MaxAlignment < AlignOfGlobal)
212 MaxAlignment = AlignOfGlobal;
221bool PPCMergeStringPool::mergeModuleStringPool(
Module &M) {
225 LLVM_DEBUG(
dbgs() <<
"Number of globals is: " <<
M.global_size() <<
"\n");
227 collectCandidateConstants(M);
235 std::sort(MergeableStrings.begin(), MergeableStrings.end(), CompareConstants);
257 LLVM_DEBUG(
dbgs() <<
"Constructing global variable for string pool: ");
261 size_t ElementIndex = 0;
270 replaceUsesWithGEP(GV, PooledGlobal, ElementIndex);
278 PooledStructType, PooledGlobal, Indices);
303void PPCMergeStringPool::replaceUsesWithGEP(
GlobalVariable *GlobalToReplace,
305 unsigned ElementIndex) {
313 for (
User *CurrentUser : GlobalToReplace->
users())
314 Users.push_back(CurrentUser);
317 Instruction *UserInstruction = dyn_cast<Instruction>(CurrentUser);
318 Constant *UserConstant = dyn_cast<Constant>(CurrentUser);
322 assert((UserConstant || UserInstruction) &&
323 "Expected the user to be an instruction or a constant.");
326 if (!userHasOperand(CurrentUser, GlobalToReplace))
330 if (isa<GlobalValue>(CurrentUser))
333 if (!UserInstruction) {
336 PooledStructType, GPool, Indices);
341 if (
PHINode *UserPHI = dyn_cast<PHINode>(UserInstruction)) {
346 PooledStructType, GPool, Indices);
347 UserPHI->replaceUsesOfWith(GlobalToReplace, ConstGEP);
364 CurrentUser->replaceUsesOfWith(GlobalToReplace, GEPInst);
370char PPCMergeStringPool::ID = 0;
376 return new PPCMergeStringPool();
This file contains the declarations for the subclasses of Constant, which represent the different fla...
iv Induction Variable Users
Module.h This file contains the declarations for the Module class.
static cl::opt< unsigned > MaxStringsPooled("ppc-max-strings-pooled", cl::Hidden, cl::init(-1), cl::desc("Maximum Number of Strings to Pool."))
static cl::opt< unsigned > MinStringsBeforePool("ppc-min-strings-before-pool", cl::Hidden, cl::init(2), cl::desc("Minimum number of string candidates before " "pooling is considered."))
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
This is the interface for a SCEV-based alias analysis.
This file defines the 'Statistic' class, which is designed to be an easy way to expose various metric...
#define STATISTIC(VARNAME, DESC)
Represent the analysis usage information of a pass.
AnalysisUsage & addPreserved()
Add the specified Pass class to the set of analyses preserved by this pass.
ConstantDataSequential - A vector or array constant whose element type is a simple 1/2/4/8-byte integ...
uint64_t getElementByteSize() const
Return the size (in bytes) of each element in the array/vector.
unsigned getNumElements() const
Return the number of elements in the array or vector.
static Constant * getInBoundsGetElementPtr(Type *Ty, Constant *C, ArrayRef< Constant * > IdxList)
Create an "inbounds" getelementptr.
static Constant * getAnon(ArrayRef< Constant * > V, bool Packed=false)
Return an anonymous struct that has the specified elements.
This is an important base class in LLVM.
void handleOperandChange(Value *, Value *)
This method is a special form of User::replaceUsesOfWith (which does not work on constants) that does...
This class represents an Operation in the Expression.
Legacy analysis pass which computes a DominatorTree.
an instruction for type-safe pointer arithmetic to access elements of arrays and structs
static GetElementPtrInst * Create(Type *PointeeType, Value *Ptr, ArrayRef< Value * > IdxList, const Twine &NameStr, BasicBlock::iterator InsertBefore)
void setAlignment(Align Align)
Sets the alignment attribute of the GlobalObject.
@ PrivateLinkage
Like Internal, but omit from symbol table.
@ InternalLinkage
Rename collisions when linking (static functions).
const Constant * getInitializer() const
getInitializer - Return the initializer for this global variable.
void eraseFromParent()
eraseFromParent - This method unlinks 'this' from the containing module and deletes it.
void insertBefore(Instruction *InsertPos)
Insert an unlinked instruction into a basic block immediately before the specified instruction.
This is an important class for using LLVM in a threaded context.
The legacy pass manager's analysis pass to compute loop information.
ModulePass class - This class is used to implement unstructured interprocedural optimizations and ana...
virtual bool runOnModule(Module &M)=0
runOnModule - Virtual method overriden by subclasses to process the module being operated on.
A Module instance is used to store all the information related to an LLVM module.
virtual void getAnalysisUsage(AnalysisUsage &) const
getAnalysisUsage - This function should be overriden by passes that need analysis information to do t...
virtual bool doInitialization(Module &)
doInitialization - Virtual method overridden by subclasses to do any necessary initialization before ...
virtual StringRef getPassName() const
getPassName - Return a nice clean name for a pass.
Legacy wrapper pass to provide the SCEVAAResult object.
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
bool contains(ConstPtrType Ptr) const
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
StringRef - Represent a constant reference to a string, i.e.
The instances of the Type class are immutable: once they are created, they are never changed.
static IntegerType * getInt32Ty(LLVMContext &C)
LLVM Value Representation.
iterator_range< user_iterator > users()
bool isUsedByMetadata() const
Return true if there is metadata referencing this value.
unsigned getNumUses() const
This method computes the number of uses of this Value.
void dump() const
Support for debugging, callable in GDB: V->dump()
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
initializer< Ty > init(const Ty &Val)
This is an optimization pass for GlobalISel generic memory operations.
ModulePass * createPPCMergeStringPoolPass()
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
@ Global
Append to llvm.global_dtors.
GlobalVariable * collectUsedGlobalVariables(const Module &M, SmallVectorImpl< GlobalValue * > &Vec, bool CompilerUsed)
Given "llvm.used" or "llvm.compiler.used" as a global name, collect the initializer elements of that ...
This struct is a compact representation of a valid (non-zero power of two) alignment.
uint64_t value() const
This is a hole in the type system and should not be abused.