diff options
Diffstat (limited to 'indra/newview')
| -rw-r--r-- | indra/newview/llmeshrepository.cpp | 71 | ||||
| -rw-r--r-- | indra/newview/llmeshrepository.h | 9 | ||||
| -rw-r--r-- | indra/newview/llvovolume.cpp | 36 | ||||
| -rw-r--r-- | indra/newview/llvovolume.h | 4 | 
4 files changed, 104 insertions, 16 deletions
| diff --git a/indra/newview/llmeshrepository.cpp b/indra/newview/llmeshrepository.cpp index d5b14dc6aa..ced64b655e 100644 --- a/indra/newview/llmeshrepository.cpp +++ b/indra/newview/llmeshrepository.cpp @@ -1972,8 +1972,16 @@ bool LLMeshRepoThread::skinInfoReceived(const LLUUID& mesh_id, U8* data, S32 dat  	}  	{ -		LLMeshSkinInfo info(skin); -		info.mMeshID = mesh_id; +		LLMeshSkinInfo* info = nullptr; +		try +		{ +			info = new LLMeshSkinInfo(mesh_id, skin); +		} +		catch (const std::bad_alloc& ex) +		{ +			LL_WARNS() << "Failed to allocate skin info with exception: " << ex.what()  << LL_ENDL; +			return false; +		}          // LL_DEBUGS(LOG_MESH) << "info pelvis offset" << info.mPelvisOffset << LL_ENDL;  		{ @@ -2898,7 +2906,7 @@ void LLMeshRepoThread::notifyLoadedMeshes()  	{  		if (mMutex->trylock())  		{ -			std::list<LLMeshSkinInfo> skin_info_q; +			std::list<LLMeshSkinInfo*> skin_info_q;  			std::list<LLModel::Decomposition*> decomp_q;  			if (! mSkinInfoQ.empty()) @@ -3491,7 +3499,7 @@ LLMeshRepository::LLMeshRepository()    mMeshThreadCount(0),    mThread(NULL)  { - +	mSkinInfoCullTimer.resetWithExpiry(10.f);  }  void LLMeshRepository::init() @@ -3776,6 +3784,28 @@ void LLMeshRepository::notifyLoadedMeshes()  	//call completed callbacks on finished decompositions  	mDecompThread->notifyCompleted(); +	if (mSkinInfoCullTimer.checkExpirationAndReset(10.f))  +	{ +		//// Clean up dead skin info +		//U64Bytes skinbytes(0); +		for (auto iter = mSkinMap.begin(), ender = mSkinMap.end(); iter != ender;) +		{ +			auto copy_iter = iter++; + +			//skinbytes += U64Bytes(sizeof(LLMeshSkinInfo)); +			//skinbytes += U64Bytes(copy_iter->second->mJointNames.size() * sizeof(std::string)); +			//skinbytes += U64Bytes(copy_iter->second->mJointNums.size() * sizeof(S32)); +			//skinbytes += U64Bytes(copy_iter->second->mJointNames.size() * sizeof(LLMatrix4a)); +			//skinbytes += U64Bytes(copy_iter->second->mJointNames.size() * sizeof(LLMatrix4)); + +			if (copy_iter->second->getNumRefs() == 1) +			{ +				mSkinMap.erase(copy_iter); +			} +		} +		//LL_INFOS() << "Skin info cache elements:" << mSkinMap.size() << " Memory: " << U64Kilobytes(skinbytes) << LL_ENDL; +	} +  	// For major operations, attempt to get the required locks  	// without blocking and punt if they're not available.  The  	// longest run of holdoffs is kept in sMaxLockHoldoffs just @@ -3913,13 +3943,13 @@ void LLMeshRepository::notifyLoadedMeshes()  	mThread->mSignal->signal();  } -void LLMeshRepository::notifySkinInfoReceived(LLMeshSkinInfo& info) +void LLMeshRepository::notifySkinInfoReceived(LLMeshSkinInfo* info)  { -	mSkinMap[info.mMeshID] = info; +	mSkinMap[info->mMeshID] = info; // Cache into LLPointer      // Alternative: We can get skin size from header -    sCacheBytesSkins += info.sizeBytes(); +    sCacheBytesSkins += info->sizeBytes(); -	skin_load_map::iterator iter = mLoadingSkins.find(info.mMeshID); +	skin_load_map::iterator iter = mLoadingSkins.find(info->mMeshID);  	if (iter != mLoadingSkins.end())  	{  		for (std::set<LLUUID>::iterator obj_id = iter->second.begin(); obj_id != iter->second.end(); ++obj_id) @@ -3927,10 +3957,27 @@ void LLMeshRepository::notifySkinInfoReceived(LLMeshSkinInfo& info)  			LLVOVolume* vobj = (LLVOVolume*) gObjectList.findObject(*obj_id);  			if (vobj)  			{ -				vobj->notifyMeshLoaded(); +				vobj->notifySkinInfoLoaded(info); +			} +		} +		mLoadingSkins.erase(iter); +	} +} + +void LLMeshRepository::notifySkinInfoUnavailable(const LLUUID& mesh_id) +{ +	skin_load_map::iterator iter = mLoadingSkins.find(mesh_id); +	if (iter != mLoadingSkins.end()) +	{ +		for (std::set<LLUUID>::iterator obj_id = iter->second.begin(); obj_id != iter->second.end(); ++obj_id) +		{ +			LLVOVolume* vobj = (LLVOVolume*) gObjectList.findObject(*obj_id); +			if (vobj) +			{ +				vobj->notifySkinInfoUnavailable();  			}  		} -		mLoadingSkins.erase(info.mMeshID); +		mLoadingSkins.erase(iter);  	}  } @@ -4042,7 +4089,7 @@ const LLMeshSkinInfo* LLMeshRepository::getSkinInfo(const LLUUID& mesh_id, const          skin_map::iterator iter = mSkinMap.find(mesh_id);          if (iter != mSkinMap.end())          { -            return &(iter->second); +            return iter->second;          }          //no skin info known about given mesh, try to fetch it @@ -4058,7 +4105,7 @@ const LLMeshSkinInfo* LLMeshRepository::getSkinInfo(const LLUUID& mesh_id, const              mLoadingSkins[mesh_id].insert(requesting_obj->getID());          }      } -	return NULL; +	return nullptr;  }  void LLMeshRepository::fetchPhysicsShape(const LLUUID& mesh_id) diff --git a/indra/newview/llmeshrepository.h b/indra/newview/llmeshrepository.h index 2cade8f01e..a5b985ee76 100644 --- a/indra/newview/llmeshrepository.h +++ b/indra/newview/llmeshrepository.h @@ -284,7 +284,7 @@ public:  	std::set<UUIDBasedRequest> mSkinRequests;  	// list of completed skin info requests -	std::list<LLMeshSkinInfo> mSkinInfoQ; +	std::list<LLMeshSkinInfo*> mSkinInfoQ;  	//set of requested decompositions  	std::set<UUIDBasedRequest> mDecompositionRequests; @@ -581,7 +581,8 @@ public:  	void notifyLoadedMeshes();  	void notifyMeshLoaded(const LLVolumeParams& mesh_params, LLVolume* volume);  	void notifyMeshUnavailable(const LLVolumeParams& mesh_params, S32 lod); -	void notifySkinInfoReceived(LLMeshSkinInfo& info); +	void notifySkinInfoReceived(LLMeshSkinInfo* info); +	void notifySkinInfoUnavailable(const LLUUID& info);  	void notifyDecompositionReceived(LLModel::Decomposition* info);  	S32 getActualMeshLOD(const LLVolumeParams& mesh_params, S32 lod); @@ -614,7 +615,7 @@ public:  	typedef boost::unordered_map<LLUUID, std::vector<LLUUID> > mesh_load_map;  	mesh_load_map mLoadingMeshes[4]; -	typedef std::unordered_map<LLUUID, LLMeshSkinInfo> skin_map; +	typedef std::unordered_map<LLUUID, LLPointer<LLMeshSkinInfo>> skin_map;  	skin_map mSkinMap;  	typedef std::map<LLUUID, LLModel::Decomposition*> decomposition_map; @@ -650,6 +651,8 @@ public:  	std::vector<LLMeshUploadThread*> mUploadWaitList;  	LLPhysicsDecomp* mDecompThread; + +	LLFrameTimer     mSkinInfoCullTimer;  	class inventory_data  	{ diff --git a/indra/newview/llvovolume.cpp b/indra/newview/llvovolume.cpp index f4a938e57d..d5583f05f3 100644 --- a/indra/newview/llvovolume.cpp +++ b/indra/newview/llvovolume.cpp @@ -228,6 +228,9 @@ LLVOVolume::LLVOVolume(const LLUUID &id, const LLPCode pcode, LLViewerRegion *re      mColorChanged = FALSE;  	mSpotLightPriority = 0.f; +	mSkinInfoFailed = false; +	mSkinInfo = NULL; +  	mMediaImplList.resize(getNumTEs());  	mLastFetchedMediaVersion = -1;      mServerDrawableUpdateCount = 0; @@ -1095,6 +1098,12 @@ BOOL LLVOVolume::setVolume(const LLVolumeParams ¶ms_in, const S32 detail, bo  			// if it's a mesh  			if ((volume_params.getSculptType() & LL_SCULPT_TYPE_MASK) == LL_SCULPT_TYPE_MESH)  			{ +				if (mSkinInfo && mSkinInfo->mMeshID != volume_params.getSculptID()) +				{ +					mSkinInfo = NULL; +					mSkinInfoFailed = false; +				} +  				if (!getVolume()->isMeshAssetLoaded())  				{   					//load request not yet issued, request pipeline load this mesh @@ -1106,6 +1115,14 @@ BOOL LLVOVolume::setVolume(const LLVolumeParams ¶ms_in, const S32 detail, bo  					}  				} +				if (!mSkinInfo && !mSkinInfoFailed) +				{ +					const LLMeshSkinInfo* skin_info = gMeshRepo.getSkinInfo(volume_params.getSculptID(), this); +					if (skin_info) +					{ +						notifySkinInfoLoaded(skin_info); +					} +				}  			}  			else // otherwise is sculptie  			{ @@ -1158,6 +1175,9 @@ void LLVOVolume::updateSculptTexture()  		{  			mSculptTexture = LLViewerTextureManager::getFetchedTexture(id, FTT_DEFAULT, TRUE, LLGLTexture::BOOST_NONE, LLViewerTexture::LOD_TEXTURE);  		} + +		mSkinInfoFailed = false; +		mSkinInfo = NULL;  	}  	else  	{ @@ -1212,6 +1232,20 @@ void LLVOVolume::notifyMeshLoaded()      updateVisualComplexity();  } +void LLVOVolume::notifySkinInfoLoaded(const LLMeshSkinInfo* skin) +{ +	mSkinInfoFailed = false; +	mSkinInfo = skin; + +	notifyMeshLoaded(); +} + +void LLVOVolume::notifySkinInfoUnavailable() +{ +	mSkinInfoFailed = true; +	mSkinInfo = nullptr; +} +  // sculpt replaces generate() for sculpted surfaces  void LLVOVolume::sculpt()  {	 @@ -3645,7 +3679,7 @@ const LLMeshSkinInfo* LLVOVolume::getSkinInfo() const  {      if (getVolume())      { -        return gMeshRepo.getSkinInfo(getMeshID(), this); +         return mSkinInfo;      }      else      { diff --git a/indra/newview/llvovolume.h b/indra/newview/llvovolume.h index 4136c13315..12681e2bd9 100644 --- a/indra/newview/llvovolume.h +++ b/indra/newview/llvovolume.h @@ -350,6 +350,8 @@ public:      void updateVisualComplexity();  	void notifyMeshLoaded(); +	void notifySkinInfoLoaded(const LLMeshSkinInfo* skin); +	void notifySkinInfoUnavailable();  	// Returns 'true' iff the media data for this object is in flight  	bool isMediaDataBeingFetched() const; @@ -433,6 +435,8 @@ private:  	LLPointer<LLRiggedVolume> mRiggedVolume; +	bool mSkinInfoFailed; +	LLConstPointer<LLMeshSkinInfo> mSkinInfo;  	// statics  public:  	static F32 sLODSlopDistanceFactor;// Changing this to zero, effectively disables the LOD transition slop | 
