LLVM API Documentation

DeadTypeElimination.cpp

Go to the documentation of this file.
00001 //===- DeadTypeElimination.cpp - Eliminate unused types for symbol table --===//
00002 //
00003 //                     The LLVM Compiler Infrastructure
00004 //
00005 // This file was developed by the LLVM research group and is distributed under
00006 // the University of Illinois Open Source License. See LICENSE.TXT for details.
00007 //
00008 //===----------------------------------------------------------------------===//
00009 //
00010 // This pass is used to cleanup the output of GCC.  It eliminate names for types
00011 // that are unused in the entire translation unit, using the FindUsedTypes pass.
00012 //
00013 //===----------------------------------------------------------------------===//
00014 
00015 #include "llvm/Transforms/IPO.h"
00016 #include "llvm/Analysis/FindUsedTypes.h"
00017 #include "llvm/Module.h"
00018 #include "llvm/SymbolTable.h"
00019 #include "llvm/DerivedTypes.h"
00020 #include "llvm/ADT/Statistic.h"
00021 using namespace llvm;
00022 
00023 namespace {
00024   struct DTE : public ModulePass {
00025     // doPassInitialization - For this pass, it removes global symbol table
00026     // entries for primitive types.  These are never used for linking in GCC and
00027     // they make the output uglier to look at, so we nuke them.
00028     //
00029     // Also, initialize instance variables.
00030     //
00031     bool runOnModule(Module &M);
00032 
00033     // getAnalysisUsage - This function needs FindUsedTypes to do its job...
00034     //
00035     virtual void getAnalysisUsage(AnalysisUsage &AU) const {
00036       AU.addRequired<FindUsedTypes>();
00037     }
00038   };
00039   RegisterOpt<DTE> X("deadtypeelim", "Dead Type Elimination");
00040   Statistic<>
00041   NumKilled("deadtypeelim", "Number of unused typenames removed from symtab");
00042 }
00043 
00044 ModulePass *llvm::createDeadTypeEliminationPass() {
00045   return new DTE();
00046 }
00047 
00048 
00049 // ShouldNukeSymtabEntry - Return true if this module level symbol table entry
00050 // should be eliminated.
00051 //
00052 static inline bool ShouldNukeSymtabEntry(const Type *Ty){
00053   // Nuke all names for primitive types!
00054   if (Ty->isPrimitiveType()) return true;
00055 
00056   // Nuke all pointers to primitive types as well...
00057   if (const PointerType *PT = dyn_cast<PointerType>(Ty))
00058     if (PT->getElementType()->isPrimitiveType()) return true;
00059 
00060   return false;
00061 }
00062 
00063 // run - For this pass, it removes global symbol table entries for primitive
00064 // types.  These are never used for linking in GCC and they make the output
00065 // uglier to look at, so we nuke them.  Also eliminate types that are never used
00066 // in the entire program as indicated by FindUsedTypes.
00067 //
00068 bool DTE::runOnModule(Module &M) {
00069   bool Changed = false;
00070 
00071   SymbolTable &ST = M.getSymbolTable();
00072   std::set<const Type *> UsedTypes = getAnalysis<FindUsedTypes>().getTypes();
00073 
00074   // Check the symbol table for superfluous type entries...
00075   //
00076   // Grab the 'type' plane of the module symbol...
00077   SymbolTable::type_iterator TI = ST.type_begin();
00078   while ( TI != ST.type_end() ) {
00079     // If this entry should be unconditionally removed, or if we detect that
00080     // the type is not used, remove it.
00081     const Type *RHS = TI->second;
00082     if (ShouldNukeSymtabEntry(RHS) || !UsedTypes.count(RHS)) {
00083       ST.remove(TI++);
00084       ++NumKilled;
00085       Changed = true;
00086     } else {
00087       ++TI;
00088       // We only need to leave one name for each type.
00089       UsedTypes.erase(RHS);
00090     }
00091   }
00092 
00093   return Changed;
00094 }
00095 
00096 // vim: sw=2