diff --git a/indra/newview/llviewerobject.cpp b/indra/newview/llviewerobject.cpp
index d5d804bc578e31c66fa945990e3c213579fee03f..ef28c3ad53e46f5c2fc534d28ab1777dfa8cd48e 100644
--- a/indra/newview/llviewerobject.cpp
+++ b/indra/newview/llviewerobject.cpp
@@ -995,7 +995,13 @@ U32 LLViewerObject::checkMediaURL(const std::string &media_url)
 U32 LLViewerObject::extractSpatialExtents(LLDataPackerBinaryBuffer *dp, LLVector3& pos, LLVector3& scale, LLQuaternion& rot)
 {
 	U32	parent_id = 0;
-	
+	LLViewerObject::unpackParentID(dp, parent_id);
+	if(parent_id > 0)
+	{
+		//is a child, no need to decode further.
+		return parent_id;
+	}
+
 	LLViewerObject::unpackVector3(dp, scale, "Scale");
 	LLViewerObject::unpackVector3(dp, pos, "Pos");
 	
@@ -1003,8 +1009,6 @@ U32 LLViewerObject::extractSpatialExtents(LLDataPackerBinaryBuffer *dp, LLVector
 	LLViewerObject::unpackVector3(dp, vec, "Rot");
 	rot.unpackFromVector3(vec);
 	
-	LLViewerObject::unpackParentID(dp, parent_id);
-	
 	return parent_id;
 }
 
diff --git a/indra/newview/llviewerregion.cpp b/indra/newview/llviewerregion.cpp
index 84e9c8ea9a4ff7f25d9fe4b2489be6df8d9fa0fd..a2ff232d027b1ab173a365598201262c9cd31b97 100644
--- a/indra/newview/llviewerregion.cpp
+++ b/indra/newview/llviewerregion.cpp
@@ -1020,11 +1020,6 @@ F32 LLViewerRegion::updateVisibleEntries(F32 max_time)
 		{
 			++iter;
 		}
-
-		//if(update_timer.getElapsedTimeF32() > max_time)
-		//{
-		//	break;
-		//}
 	}
 #endif
 
@@ -1046,24 +1041,14 @@ F32 LLViewerRegion::updateVisibleEntries(F32 max_time)
 
 				if(vo_entry->getParentID() > 0) //is a child
 				{
-					LLVOCacheEntry* parent = getCacheEntry(vo_entry->getParentID());
-					
-					//make sure the parent is active
-					if(!parent || !parent->isState(LLVOCacheEntry::ACTIVE))
-					{
-						continue;
-					}
+					//child visibility depends on its parent.
+					continue;
 				}
 
 				vo_entry->calcSceneContribution(camera_origin, needs_update, mImpl->mLastCameraUpdate);				
 				mImpl->mWaitingList.insert(vo_entry);
 			}
 		}
-
-		//if(update_timer.getElapsedTimeF32() > max_time)
-		//{
-		//	break;
-		//}
 	}
 	mImpl->mVisibleGroups.clear();
 
@@ -1145,6 +1130,7 @@ BOOL LLViewerRegion::idleUpdate(F32 max_update_time)
 
 F32 LLViewerRegion::killInvisibleObjects(F32 max_time)
 {
+#if 1
 	if(!sVOCacheCullingEnabled)
 	{
 		return max_time;
@@ -1164,7 +1150,7 @@ F32 LLViewerRegion::killInvisibleObjects(F32 max_time)
 		gObjectList.killObject(delete_list[i]->getVObj());
 	}
 	delete_list.clear();
-
+#endif
 	return max_time;
 }
 
@@ -1694,15 +1680,15 @@ void LLViewerRegion::setSimulatorFeatures(const LLSD& sim_features)
 //move all orphan children out of cache and insert to rendering octree.
 void LLViewerRegion::findOrphans(U32 parent_id)
 {
-	std::map<U32, OrphanList>::iterator iter = mOrphanMap.find(parent_id);
+	orphan_list_t::iterator iter = mOrphanMap.find(parent_id);
 	if(iter != mOrphanMap.end())
 	{
-		std::set<U32>* children = mOrphanMap[parent_id].getChildList();
-		for(std::set<U32>::iterator child_iter = children->begin(); child_iter != children->end(); ++child_iter)
+		std::vector<U32>* children = &mOrphanMap[parent_id];
+		for(S32 i = 0; i < children->size(); i++)
 		{
-			forceToRemoveFromCache(*child_iter, NULL);
+			forceToRemoveFromCache((*children)[i], NULL);
 		}
-			
+		children->clear();
 		mOrphanMap.erase(parent_id);
 	}
 }
@@ -1727,58 +1713,42 @@ void LLViewerRegion::decodeBoundingInfo(LLVOCacheEntry* entry)
 	LLVector3 pos;
 	LLVector3 scale;
 	LLQuaternion rot;
+
+	//decode spatial info and parent info
 	U32 parent_id = LLViewerObject::extractSpatialExtents(entry->getDP(), pos, scale, rot);
 	
-	entry->setBoundingInfo(pos, scale);
-	
 	if(parent_id > 0) //has parent
 	{
 		entry->setParentID(parent_id);
 	
-		//1, find parent, update position
+		//1, find the parent in cache
 		LLVOCacheEntry* parent = getCacheEntry(parent_id);
 		
-		//2, if can not, put into the orphan list.
-		if(!parent || !parent->getGroup())
+		//2, parent is not in the cache, put into the orphan list.
+		if(!parent)
 		{
-			std::map<U32, OrphanList>::iterator iter = mOrphanMap.find(parent_id);
-			if(iter != mOrphanMap.end())
+			mOrphanMap[parent_id].push_back(entry->getLocalID());
+		}
+		else //parent in cache
+		{
+			if(!parent->isState(LLVOCacheEntry::INACTIVE)) 
 			{
-				iter->second.addChild(entry->getLocalID());
+				//parent is visible, so is the child.
+				addVisibleCacheEntry(entry);
 			}
-			else 
+			else
 			{
-				//check if the parent is an uncacheable object
-				if(!parent)
-				{
-					LLUUID parent_uuid;
-					LLViewerObjectList::getUUIDFromLocal(parent_uuid,
-															parent_id,
-															getHost().getAddress(),
-															getHost().getPort());
-					LLViewerObject *parent_objp = gObjectList.findObject(parent_uuid);
-					if(parent_objp)
-					{
-						//parent is not cacheable, remove child from the cache.
-						forceToRemoveFromCache(entry->getLocalID(), NULL);
-						return;
-					}
-				}
-
-				//otherwise insert to the orphan list
-				OrphanList o_list(entry->getLocalID());
-				mOrphanMap[parent_id] = o_list;
+				parent->addChild(entry);
 			}
-			
-			return;
-		}
-		else
-		{
-			//update the child position to the region space.
-			entry->updateBoundingInfo(parent);
 		}
+
+		return;
 	}
 	
+	//
+	//no parent
+	//
+	entry->setBoundingInfo(pos, scale);
 	if(!entry->getGroup() && entry->isState(LLVOCacheEntry::INACTIVE))
 	{
 		addToVOCacheTree(entry);
@@ -1787,21 +1757,20 @@ void LLViewerRegion::decodeBoundingInfo(LLVOCacheEntry* entry)
 	if(!parent_id) //a potential parent
 	{
 		//find all children and update their bounding info
-		std::map<U32, OrphanList>::iterator iter = mOrphanMap.find(entry->getLocalID());
+		orphan_list_t::iterator iter = mOrphanMap.find(entry->getLocalID());
 		if(iter != mOrphanMap.end())
-		{
-			std::set<U32>* children = mOrphanMap[parent_id].getChildList();
-			for(std::set<U32>::iterator child_iter = children->begin(); child_iter != children->end(); ++child_iter)
+		{			
+			std::vector<U32>* orphans = &mOrphanMap[entry->getLocalID()];
+			S32 size = orphans->size();
+			for(S32 i = 0; i < size; i++)
 			{
-				LLVOCacheEntry* child = getCacheEntry(*child_iter);
+				LLVOCacheEntry* child = getCacheEntry((*orphans)[i]);
 				if(child)
 				{
-					//update the child position to the region space.
-					child->updateBoundingInfo(entry);
-					addToVOCacheTree(child);
+					entry->addChild(child);
 				}
 			}
-			
+			orphans->clear();
 			mOrphanMap.erase(entry->getLocalID());
 		}
 	}
diff --git a/indra/newview/llviewerregion.h b/indra/newview/llviewerregion.h
index 2248cf526916b459847754b55c0287a5897d3d08..410c903f18ce59034da882026618cbdc82825f34 100644
--- a/indra/newview/llviewerregion.h
+++ b/indra/newview/llviewerregion.h
@@ -447,21 +447,9 @@ class LLViewerRegion: public LLCapabilityProvider // implements this interface
 	BOOL	mCapabilitiesReceived;
 	BOOL    mReleaseNotesRequested;
 	BOOL    mDead;  //if true, this region is in the process of deleting.
-
-	class OrphanList
-	{
-	public:
-		OrphanList(){}
-		OrphanList(U32 child_id){addChild(child_id);}
-		
-		void addChild(U32 child_id) {mChildList.insert(child_id);}
-		std::set<U32>* getChildList() {return &mChildList;}
-		
-	private:
-		std::set<U32> mChildList;
-	};
 	
-	std::map<U32, OrphanList> mOrphanMap;
+	typedef std::map<U32, std::vector<U32> > orphan_list_t;
+	orphan_list_t mOrphanMap;
 	
 	class CacheMissItem
 	{
@@ -471,21 +459,9 @@ class LLViewerRegion: public LLCapabilityProvider // implements this interface
 		U32                            mID;     //local object id
 		LLViewerRegion::eCacheMissType mType;   //cache miss type
 	
-#if 0
-		struct Compare
-		{
-			bool operator()(const CacheMissItem& lhs, const CacheMissItem& rhs)
-			{
-				return lhs.mID < rhs.mID; //smaller ID first.
-			}
-		};
-
-		typedef std::set<CacheMissItem, Compare> cache_miss_list_t;
-#else
 		typedef std::list<CacheMissItem> cache_miss_list_t;
-#endif
 	};
-	CacheMissItem::cache_miss_list_t        mCacheMissList;
+	CacheMissItem::cache_miss_list_t   mCacheMissList;
 	
 	caps_received_signal_t mCapabilitiesReceivedSignal;		
 	LLSD mSimulatorFeatures;
diff --git a/indra/newview/llvocache.cpp b/indra/newview/llvocache.cpp
index 1dd149631afb7b5a87d5fcd64812e341bdf78d2c..eba768fef4f17abc9a8a08f8f3437c7504c8243b 100644
--- a/indra/newview/llvocache.cpp
+++ b/indra/newview/llvocache.cpp
@@ -367,14 +367,6 @@ void LLVOCacheEntry::setBoundingInfo(const LLVector3& pos, const LLVector3& scal
 	setBinRadius(llmin(size.getLength3().getF32() * 4.f, 256.f));
 }
 
-void LLVOCacheEntry::updateBoundingInfo(LLVOCacheEntry* parent)
-{
-	//LLVector4a old_pos = getPositionGroup();
-	//parent->getPositionRegion() + (getPosition() * parent->getRotation());
-	
-	shift(parent->getPositionGroup());
-}
-
 //-------------------------------------------------------------------
 //LLVOCachePartition
 //-------------------------------------------------------------------
@@ -593,7 +585,12 @@ void LLVOCache::removeCache(ELLPath location, bool started)
 
 void LLVOCache::removeCache() 
 {
-	llassert_always(mInitialized) ;
+	if(!mInitialized)
+	{
+		//OK to remove cache even it is not initialized.
+		llwarns << "Object cache is not initialized yet." << llendl;
+	}
+
 	if(mReadOnly)
 	{
 		llwarns << "Not clearing object cache: Cache is currently in read-only mode." << llendl;
diff --git a/indra/newview/llvocache.h b/indra/newview/llvocache.h
index 4b775a4288843c51c2fe3db8394e0ffb0ebbf6e0..2aec88537caf30d64f0bcc3728ea1d7aca9caa48 100644
--- a/indra/newview/llvocache.h
+++ b/indra/newview/llvocache.h
@@ -114,8 +114,7 @@ class LLVOCacheEntry : public LLViewerOctreeEntryData
 
 	//called from processing object update message
 	void setBoundingInfo(const LLVector3& pos, const LLVector3& scale);
-	void updateBoundingInfo(LLVOCacheEntry* parent);
-
+	
 	void setTouched(BOOL touched = TRUE) {mTouched = touched;}
 	BOOL isTouched() const {return mTouched;}