Fix Transforms/DeadArgElim/2007-02-07-FuncRename.ll, fallout from PR411.
[oota-llvm.git] / lib / Transforms / IPO / DeadTypeElimination.cpp
1 //===- DeadTypeElimination.cpp - Eliminate unused types for symbol table --===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file was developed by the LLVM research group and is distributed under
6 // the University of Illinois Open Source License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This pass is used to cleanup the output of GCC.  It eliminate names for types
11 // that are unused in the entire translation unit, using the FindUsedTypes pass.
12 //
13 //===----------------------------------------------------------------------===//
14
15 #define DEBUG_TYPE "deadtypeelim"
16 #include "llvm/Transforms/IPO.h"
17 #include "llvm/Analysis/FindUsedTypes.h"
18 #include "llvm/Module.h"
19 #include "llvm/TypeSymbolTable.h"
20 #include "llvm/DerivedTypes.h"
21 #include "llvm/ADT/Statistic.h"
22 #include "llvm/Support/Compiler.h"
23 using namespace llvm;
24
25 STATISTIC(NumKilled, "Number of unused typenames removed from symtab");
26
27 namespace {
28   struct VISIBILITY_HIDDEN DTE : public ModulePass {
29     // doPassInitialization - For this pass, it removes global symbol table
30     // entries for primitive types.  These are never used for linking in GCC and
31     // they make the output uglier to look at, so we nuke them.
32     //
33     // Also, initialize instance variables.
34     //
35     bool runOnModule(Module &M);
36
37     // getAnalysisUsage - This function needs FindUsedTypes to do its job...
38     //
39     virtual void getAnalysisUsage(AnalysisUsage &AU) const {
40       AU.addRequired<FindUsedTypes>();
41     }
42   };
43   RegisterPass<DTE> X("deadtypeelim", "Dead Type Elimination");
44 }
45
46 ModulePass *llvm::createDeadTypeEliminationPass() {
47   return new DTE();
48 }
49
50
51 // ShouldNukeSymtabEntry - Return true if this module level symbol table entry
52 // should be eliminated.
53 //
54 static inline bool ShouldNukeSymtabEntry(const Type *Ty){
55   // Nuke all names for primitive types!
56   if (Ty->isPrimitiveType() || Ty->isInteger()) 
57     return true;
58
59   // Nuke all pointers to primitive types as well...
60   if (const PointerType *PT = dyn_cast<PointerType>(Ty))
61     if (PT->getElementType()->isPrimitiveType() ||
62         PT->getElementType()->isInteger()) 
63       return true;
64
65   return false;
66 }
67
68 // run - For this pass, it removes global symbol table entries for primitive
69 // types.  These are never used for linking in GCC and they make the output
70 // uglier to look at, so we nuke them.  Also eliminate types that are never used
71 // in the entire program as indicated by FindUsedTypes.
72 //
73 bool DTE::runOnModule(Module &M) {
74   bool Changed = false;
75
76   TypeSymbolTable &ST = M.getTypeSymbolTable();
77   std::set<const Type *> UsedTypes = getAnalysis<FindUsedTypes>().getTypes();
78
79   // Check the symbol table for superfluous type entries...
80   //
81   // Grab the 'type' plane of the module symbol...
82   TypeSymbolTable::iterator TI = ST.begin();
83   TypeSymbolTable::iterator TE = ST.end();
84   while ( TI != TE ) {
85     // If this entry should be unconditionally removed, or if we detect that
86     // the type is not used, remove it.
87     const Type *RHS = TI->second;
88     if (ShouldNukeSymtabEntry(RHS) || !UsedTypes.count(RHS)) {
89       ST.remove(TI++);
90       ++NumKilled;
91       Changed = true;
92     } else {
93       ++TI;
94       // We only need to leave one name for each type.
95       UsedTypes.erase(RHS);
96     }
97   }
98
99   return Changed;
100 }
101
102 // vim: sw=2