Dramatically simplify DerivedType::refineAbstractTypeToInternal

This makes use of the new PATypeHolder's to keep types from being deleted
prematurely, instead of the wierd "self reference" garbage.  This is easier
to understand and more efficient as well.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@8834 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Chris Lattner 2003-10-03 04:48:21 +00:00
parent 1c5164e9cf
commit 8ef852f4ea

View File

@ -1032,13 +1032,9 @@ void DerivedType::refineAbstractTypeToInternal(const Type *NewType, bool inMap){
cast<DerivedType>(NewType)->addRef(); cast<DerivedType>(NewType)->addRef();
// Add a self use of the current type so that we don't delete ourself until // Add a self use of the current type so that we don't delete ourself until
// after this while loop. We are careful to never invoke refine on ourself, // after the function exits.
// so this extra reference shouldn't be a problem. Note that we must only
// remove a single reference at the end, but we must tolerate multiple self
// references because we could be refineAbstractTypeTo'ing recursively on the
// same type.
// //
addAbstractTypeUser(this); PATypeHolder CurrentTy(this);
// To make the situation simpler, we ask the subclass to remove this type from // To make the situation simpler, we ask the subclass to remove this type from
// the type map, and to replace any type uses with uses of non-abstract types. // the type map, and to replace any type uses with uses of non-abstract types.
@ -1046,22 +1042,15 @@ void DerivedType::refineAbstractTypeToInternal(const Type *NewType, bool inMap){
// ourselves in. // ourselves in.
dropAllTypeUses(inMap); dropAllTypeUses(inMap);
// Count the number of self uses. Stop looping when sizeof(list) == NSU.
unsigned NumSelfUses = 0;
// Iterate over all of the uses of this type, invoking callback. Each user // Iterate over all of the uses of this type, invoking callback. Each user
// should remove itself from our use list automatically. We have to check to // should remove itself from our use list automatically. We have to check to
// make sure that NewTy doesn't _become_ 'this'. If it does, resolving types // make sure that NewTy doesn't _become_ 'this'. If it does, resolving types
// will not cause users to drop off of the use list. If we resolve to ourself // will not cause users to drop off of the use list. If we resolve to ourself
// we succeed! // we succeed!
// //
while (AbstractTypeUsers.size() > NumSelfUses && NewTy != this) { while (!AbstractTypeUsers.empty() && NewTy != this) {
AbstractTypeUser *User = AbstractTypeUsers.back(); AbstractTypeUser *User = AbstractTypeUsers.back();
if (User == this) {
// Move self use to the start of the list. Increment NSU.
std::swap(AbstractTypeUsers.back(), AbstractTypeUsers[NumSelfUses++]);
} else {
unsigned OldSize = AbstractTypeUsers.size(); unsigned OldSize = AbstractTypeUsers.size();
#ifdef DEBUG_MERGE_TYPES #ifdef DEBUG_MERGE_TYPES
std::cerr << " REFINING user " << OldSize-1 << "[" << (void*)User std::cerr << " REFINING user " << OldSize-1 << "[" << (void*)User
@ -1086,19 +1075,11 @@ void DerivedType::refineAbstractTypeToInternal(const Type *NewType, bool inMap){
assert(AbstractTypeUsers.size() != OldSize && assert(AbstractTypeUsers.size() != OldSize &&
"AbsTyUser did not remove self from user list!"); "AbsTyUser did not remove self from user list!");
} }
}
// Remove a single self use, even though there may be several here. This will // If we were successful removing all users from the type, 'this' will be
// probably 'delete this', so no instance variables may be used after this // deleted when the last PATypeHolder is destroyed or updated from this type.
// occurs... // This may occur on exit of this function, as the CurrentTy object is
// // destroyed.
assert((NewTy == this || AbstractTypeUsers.back() == this) &&
"Only self uses should be left!");
#if 0
assert(AbstractTypeUsers.size() == 1 && "This type should get deleted!");
#endif
removeAbstractTypeUser(this);
} }
// typeIsRefined - Notify AbstractTypeUsers of this type that the current type // typeIsRefined - Notify AbstractTypeUsers of this type that the current type