[llvm-commits] CVS: llvm/lib/VMCore/TypeSymbolTable.cpp ValueSymbolTable.cpp

Reid Spencer reid at x10sys.com
Tue Jan 10 01:52:01 PST 2006



Changes in directory llvm/lib/VMCore:

TypeSymbolTable.cpp added (r1.1)
ValueSymbolTable.cpp added (r1.1)
---
Log message:

For PR411: http://llvm.cs.uiuc.edu/PR411 :
First step in refactoring the SymbolTable is to split it into two classes,
one for a symbol table of types and one for a symbol table of Values. 


---
Diffs of the changes:  (+360 -0)

 TypeSymbolTable.cpp  |  193 +++++++++++++++++++++++++++++++++++++++++++++++++++
 ValueSymbolTable.cpp |  167 ++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 360 insertions(+)


Index: llvm/lib/VMCore/TypeSymbolTable.cpp
diff -c /dev/null llvm/lib/VMCore/TypeSymbolTable.cpp:1.1
*** /dev/null	Tue Jan 10 03:51:58 2006
--- llvm/lib/VMCore/TypeSymbolTable.cpp	Tue Jan 10 03:51:48 2006
***************
*** 0 ****
--- 1,193 ----
+ //===-- TypeSymbolTable.cpp - Implement the TypeSymbolTable class ---------===//
+ //
+ //                     The LLVM Compiler Infrastructure
+ //
+ // This file was developed by the LLVM research group and revised by Reid
+ // Spencer. It is distributed under the University of Illinois Open Source
+ // License. See LICENSE.TXT for details.
+ //
+ //===----------------------------------------------------------------------===//
+ //
+ // This file implements the TypeSymbolTable class for the VMCore library.
+ //
+ //===----------------------------------------------------------------------===//
+ 
+ #include "llvm/TypeSymbolTable.h"
+ #include "llvm/DerivedTypes.h"
+ #include "llvm/ADT/StringExtras.h"
+ #include <iostream>
+ 
+ using namespace llvm;
+ 
+ #define DEBUG_SYMBOL_TABLE 0
+ #define DEBUG_ABSTYPE 0
+ 
+ TypeSymbolTable::~TypeSymbolTable() {
+   // Drop all abstract type references in the type plane...
+   for (iterator TI = tmap.begin(), TE = tmap.end(); TI != TE; ++TI) {
+     if (TI->second->isAbstract())   // If abstract, drop the reference...
+       cast<DerivedType>(TI->second)->removeAbstractTypeUser(this);
+   }
+ }
+ 
+ std::string TypeSymbolTable::getUniqueName(const std::string &BaseName) const {
+   std::string TryName = BaseName;
+   const_iterator End = tmap.end();
+ 
+   // See if the name exists
+   while (tmap.find(TryName) != End)            // Loop until we find a free
+     TryName = BaseName + utostr(++LastUnique); // name in the symbol table
+   return TryName;
+ }
+ 
+ // lookup a type by name - returns null on failure
+ Type* TypeSymbolTable::lookup(const std::string& Name) const {
+   const_iterator TI = tmap.find(Name);
+   if (TI != tmap.end())
+     return const_cast<Type*>(TI->second);
+   return 0;
+ }
+ 
+ // Erase a specific type from the symbol table
+ bool TypeSymbolTable::erase(Type *N) {
+   for (iterator TI = tmap.begin(), TE = tmap.end(); TI != TE; ++TI) {
+     if (TI->second == N) {
+       this->erase(TI);
+       return true;
+     }
+   }
+   return false;
+ }
+ 
+ // remove - Remove a type from the symbol table...
+ Type* TypeSymbolTable::erase(iterator Entry) {
+   assert(Entry != tmap.end() && "Invalid entry to remove!");
+ 
+   const Type* Result = Entry->second;
+ 
+ #if DEBUG_SYMBOL_TABLE
+   dump();
+   std::cerr << " Removing Value: " << Result->getName() << "\n";
+ #endif
+ 
+   tmap.erase(Entry);
+ 
+   // If we are removing an abstract type, remove the symbol table from it's use
+   // list...
+   if (Result->isAbstract()) {
+ #if DEBUG_ABSTYPE
+     std::cerr << "Removing abstract type from symtab" << Result->getDescription()<<"\n";
+ #endif
+     cast<DerivedType>(Result)->removeAbstractTypeUser(this);
+   }
+ 
+   return const_cast<Type*>(Result);
+ }
+ 
+ 
+ // insert - Insert a type into the symbol table with the specified name...
+ void TypeSymbolTable::insert(const std::string& Name, const Type* T) {
+   assert(T && "Can't insert null type into symbol table!");
+ 
+   // Check to see if there is a naming conflict.  If so, rename this type!
+   std::string UniqueName = Name;
+   if (lookup(Name))
+     UniqueName = getUniqueName(Name);
+ 
+ #if DEBUG_SYMBOL_TABLE
+   dump();
+   std::cerr << " Inserting type: " << UniqueName << ": "
+             << T->getDescription() << "\n";
+ #endif
+ 
+   // Insert the tmap entry
+   tmap.insert(make_pair(UniqueName, T));
+ 
+   // If we are adding an abstract type, add the symbol table to it's use list.
+   if (T->isAbstract()) {
+     cast<DerivedType>(T)->addAbstractTypeUser(this);
+ #if DEBUG_ABSTYPE
+     std::cerr << "Added abstract type to ST: " << T->getDescription() << "\n";
+ #endif
+   }
+ }
+ 
+ // Strip the symbol table of its names.
+ bool TypeSymbolTable::strip() {
+   bool RemovedSymbol = false;
+   for (iterator TI = tmap.begin(); TI != tmap.end(); ) {
+     erase(TI++);
+     RemovedSymbol = true;
+   }
+ 
+   return RemovedSymbol;
+ }
+ 
+ /// rename - Given a value with a non-empty name, remove its existing entry
+ /// from the symbol table and insert a new one for Name.  This is equivalent to
+ /// doing "remove(V), V->Name = Name, insert(V)", but is faster, and will not
+ /// temporarily remove the symbol table plane if V is the last value in the
+ /// symtab with that name (which could invalidate iterators to that plane).
+ bool TypeSymbolTable::rename(Type *T, const std::string &name) {
+   for (iterator TI = tmap.begin(), TE = tmap.end(); TI != TE; ++TI) {
+     if (TI->second == T) {
+       // Remove the old entry.
+       tmap.erase(TI);
+       // Add the new entry.
+       this->insert(name,T);
+       return true;
+     }
+   }
+   return false;
+ }
+ 
+ // This function is called when one of the types in the type plane are refined
+ void TypeSymbolTable::refineAbstractType(const DerivedType *OldType,
+                                          const Type *NewType) {
+ 
+   // Loop over all of the types in the symbol table, replacing any references
+   // to OldType with references to NewType.  Note that there may be multiple
+   // occurrences, and although we only need to remove one at a time, it's
+   // faster to remove them all in one pass.
+   //
+   for (iterator I = begin(), E = end(); I != E; ++I) {
+     if (I->second == (Type*)OldType) {  // FIXME when Types aren't const.
+ #if DEBUG_ABSTYPE
+       std::cerr << "Removing type " << OldType->getDescription() << "\n";
+ #endif
+       OldType->removeAbstractTypeUser(this);
+ 
+       I->second = (Type*)NewType;  // TODO FIXME when types aren't const
+       if (NewType->isAbstract()) {
+ #if DEBUG_ABSTYPE
+         std::cerr << "Added type " << NewType->getDescription() << "\n";
+ #endif
+         cast<DerivedType>(NewType)->addAbstractTypeUser(this);
+       }
+     }
+   }
+ }
+ 
+ 
+ // Handle situation where type becomes Concreate from Abstract
+ void TypeSymbolTable::typeBecameConcrete(const DerivedType *AbsTy) {
+   // Loop over all of the types in the symbol table, dropping any abstract
+   // type user entries for AbsTy which occur because there are names for the
+   // type.
+   for (iterator TI = begin(), TE = end(); TI != TE; ++TI)
+     if (TI->second == const_cast<Type*>(static_cast<const Type*>(AbsTy)))
+       AbsTy->removeAbstractTypeUser(this);
+ }
+ 
+ static void DumpTypes(const std::pair<const std::string, const Type*>& T ) {
+   std::cerr << "  '" << T.first << "' = ";
+   T.second->dump();
+   std::cerr << "\n";
+ }
+ 
+ void TypeSymbolTable::dump() const {
+   std::cerr << "TypeSymbolPlane: ";
+   for_each(tmap.begin(), tmap.end(), DumpTypes);
+ }
+ 
+ // vim: sw=2 ai


Index: llvm/lib/VMCore/ValueSymbolTable.cpp
diff -c /dev/null llvm/lib/VMCore/ValueSymbolTable.cpp:1.1
*** /dev/null	Tue Jan 10 03:52:01 2006
--- llvm/lib/VMCore/ValueSymbolTable.cpp	Tue Jan 10 03:51:48 2006
***************
*** 0 ****
--- 1,167 ----
+ //===-- ValueSymbolTable.cpp - Implement the ValueSymbolTable class -------===//
+ //
+ //                     The LLVM Compiler Infrastructure
+ //
+ // This file was developed by the LLVM research group and revised by Reid
+ // Spencer. It is distributed under the University of Illinois Open Source
+ // License. See LICENSE.TXT for details.
+ //
+ //===----------------------------------------------------------------------===//
+ //
+ // This file implements the ValueSymbolTable class for the VMCore library.
+ //
+ //===----------------------------------------------------------------------===//
+ 
+ #include "llvm/GlobalValue.h"
+ #include "llvm/Type.h"
+ #include "llvm/ValueSymbolTable.h"
+ #include "llvm/ADT/StringExtras.h"
+ #include <algorithm>
+ #include <iostream>
+ 
+ using namespace llvm;
+ 
+ #define DEBUG_SYMBOL_TABLE 0
+ #define DEBUG_ABSTYPE 0
+ 
+ // Class destructor
+ ValueSymbolTable::~ValueSymbolTable() {
+ #ifndef NDEBUG   // Only do this in -g mode...
+   bool LeftoverValues = true;
+   for (iterator VI = vmap.begin(), VE = vmap.end(); VI != VE; ++VI)
+     if (!isa<Constant>(VI->second) ) {
+       std::cerr << "Value still in symbol table! Type = '"
+                 << VI->second->getType()->getDescription() << "' Name = '"
+                 << VI->first << "'\n";
+       LeftoverValues = false;
+     }
+   assert(LeftoverValues && "Values remain in symbol table!");
+ #endif
+ }
+ 
+ // getUniqueName - Given a base name, return a string that is either equal to
+ // it (or derived from it) that does not already occur in the symbol table for
+ // the specified type.
+ //
+ std::string ValueSymbolTable::getUniqueName(const std::string &BaseName) const {
+   std::string TryName = BaseName;
+   const_iterator End = vmap.end();
+ 
+   // See if the name exists
+   while (vmap.find(TryName) != End)            // Loop until we find a free
+     TryName = BaseName + utostr(++LastUnique); // name in the symbol table
+   return TryName;
+ }
+ 
+ 
+ // lookup a value - Returns null on failure...
+ //
+ Value *ValueSymbolTable::lookup(const std::string &Name) const {
+   const_iterator VI = vmap.find(Name);
+   if (VI != vmap.end())                   // We found the symbol
+     return const_cast<Value*>(VI->second);
+   return 0;
+ }
+ 
+ // Strip the symbol table of its names.
+ //
+ bool ValueSymbolTable::strip() {
+   bool RemovedSymbol = false;
+   for (iterator VI = vmap.begin(), VE = vmap.end(); VI != VE; ) {
+     Value *V = VI->second;
+     ++VI;
+     if (!isa<GlobalValue>(V) || cast<GlobalValue>(V)->hasInternalLinkage()) {
+       // Set name to "", removing from symbol table!
+       V->setName("");
+       RemovedSymbol = true;
+     }
+   }
+   return RemovedSymbol;
+ }
+ 
+ // Insert a value into the symbol table with the specified name...
+ //
+ void ValueSymbolTable::insert(Value* V) {
+   assert(V && "Can't insert null Value into symbol table!");
+   assert(V->hasName() && "Can't insert nameless Value into symbol table");
+ 
+   // Check to see if there is a naming conflict.  If so, rename this type!
+   std::string UniqueName = getUniqueName(V->getName());
+ 
+ #if DEBUG_SYMBOL_TABLE
+   dump();
+   std::cerr << " Inserting value: " << UniqueName << ": " << V->dump() << "\n";
+ #endif
+ 
+   // Insert the vmap entry
+   vmap.insert(make_pair(UniqueName, V));
+ }
+ 
+ // Remove a value
+ bool ValueSymbolTable::erase(Value *V) {
+   assert(V->hasName() && "Value doesn't have name!");
+   iterator Entry = vmap.find(V->getName());
+   if (Entry == vmap.end())
+     return false;
+ 
+ #if DEBUG_SYMBOL_TABLE
+   dump();
+   std::cerr << " Removing Value: " << Entry->second->getName() << "\n";
+ #endif
+ 
+   // Remove the value from the plane...
+   vmap.erase(Entry);
+   return true;
+ }
+ 
+ 
+ // rename - Given a value with a non-empty name, remove its existing entry
+ // from the symbol table and insert a new one for Name.  This is equivalent to
+ // doing "remove(V), V->Name = Name, insert(V)", 
+ //
+ bool ValueSymbolTable::rename(Value *V, const std::string &name) {
+   assert(V && "Can't rename a null Value");
+   assert(V->hasName() && "Can't rename a nameless Value");
+   assert(!V->getName().empty() && "Can't rename an Value with null name");
+   assert(V->getName() != name && "Can't rename a Value with same name");
+   assert(!name.empty() && "Can't rename a named Value with a null name");
+ 
+   // Find the name
+   iterator VI = vmap.find(V->getName());
+ 
+   // If we didn't find it, we're done
+   if (VI == vmap.end())
+     return false;
+ 
+   // Remove the old entry.
+   vmap.erase(VI);
+ 
+   // See if we can insert the new name.
+   VI = vmap.lower_bound(name);
+ 
+   // Is there a naming conflict?
+   if (VI != vmap.end() && VI->first == name) {
+     V->Name = getUniqueName( name);
+     vmap.insert(make_pair(V->Name, V));
+   } else {
+     V->Name = name;
+     vmap.insert(VI, make_pair(name, V));
+   }
+ 
+   return true;
+ }
+ 
+ // DumpVal - a std::for_each function for dumping a value
+ //
+ static void DumpVal(const std::pair<const std::string, Value *> &V) {
+   std::cerr << "  '" << V.first << "' = ";
+   V.second->dump();
+   std::cerr << "\n";
+ }
+ 
+ // dump - print out the symbol table
+ //
+ void ValueSymbolTable::dump() const {
+   std::cerr << "ValueSymbolTable:\n";
+   for_each(vmap.begin(), vmap.end(), DumpVal);
+ }






More information about the llvm-commits mailing list