summaryrefslogtreecommitdiff
path: root/indra/llmessage/llassetstorage.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'indra/llmessage/llassetstorage.cpp')
-rw-r--r--indra/llmessage/llassetstorage.cpp330
1 files changed, 228 insertions, 102 deletions
diff --git a/indra/llmessage/llassetstorage.cpp b/indra/llmessage/llassetstorage.cpp
index 2c8e7ce8a6..b26d412e9f 100644
--- a/indra/llmessage/llassetstorage.cpp
+++ b/indra/llmessage/llassetstorage.cpp
@@ -2,30 +2,25 @@
* @file llassetstorage.cpp
* @brief Implementation of the base asset storage system.
*
- * $LicenseInfo:firstyear=2001&license=viewergpl$
- *
- * Copyright (c) 2001-2007, Linden Research, Inc.
- *
+ * $LicenseInfo:firstyear=2001&license=viewerlgpl$
* Second Life Viewer Source Code
- * The source code in this file ("Source Code") is provided by Linden Lab
- * to you under the terms of the GNU General Public License, version 2.0
- * ("GPL"), unless you have obtained a separate licensing agreement
- * ("Other License"), formally executed by you and Linden Lab. Terms of
- * the GPL can be found in doc/GPL-license.txt in this distribution, or
- * online at http://secondlife.com/developers/opensource/gplv2
+ * Copyright (C) 2010, Linden Research, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation;
+ * version 2.1 of the License only.
*
- * There are special exceptions to the terms and conditions of the GPL as
- * it is applied to this Source Code. View the full text of the exception
- * in the file doc/FLOSS-exception.txt in this software distribution, or
- * online at http://secondlife.com/developers/opensource/flossexception
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
*
- * By copying, modifying or distributing this software, you acknowledge
- * that you have read and understood your obligations described above,
- * and agree to abide by those obligations.
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
- * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
- * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
- * COMPLETENESS OR PERFORMANCE.
+ * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
* $/LicenseInfo$
*/
@@ -42,6 +37,7 @@
#include "llstring.h"
#include "lldir.h"
#include "llsd.h"
+#include "llframetimer.h"
// this library includes
#include "message.h"
@@ -58,7 +54,13 @@
LLAssetStorage *gAssetStorage = NULL;
LLMetrics *LLAssetStorage::metric_recipient = NULL;
-const LLUUID CATEGORIZE_LOST_AND_FOUND_ID("00000000-0000-0000-0000-000000000010");
+const LLUUID CATEGORIZE_LOST_AND_FOUND_ID(std::string("00000000-0000-0000-0000-000000000010"));
+
+const U64 TOXIC_ASSET_LIFETIME = (120 * 1000000); // microseconds
+
+LLTempAssetStorage::~LLTempAssetStorage()
+{
+}
///----------------------------------------------------------------------------
/// LLAssetInfo
@@ -133,20 +135,20 @@ void LLAssetInfo::setFromNameValue( const LLNameValue& nv )
str.assign( nv.mName );
pos1 = str.find('|');
buf.assign( str, 0, pos1++ );
- mType = LLAssetType::lookup( buf.c_str() );
+ mType = LLAssetType::lookup( buf );
buf.assign( str, pos1, std::string::npos );
- mUuid.set( buf.c_str() );
+ mUuid.set( buf );
// convert the value to useful information
str.assign( nv.getAsset() );
pos1 = str.find('|');
buf.assign( str, 0, pos1++ );
- mCreatorID.set( buf.c_str() );
+ mCreatorID.set( buf );
pos2 = str.find( '|', pos1 );
buf.assign( str, pos1, (pos2++) - pos1 );
- setName( buf.c_str() );
+ setName( buf );
buf.assign( str, pos2, std::string::npos );
- setDescription( buf.c_str() );
+ setDescription( buf );
llinfos << "uuid: " << mUuid << llendl;
llinfos << "creator: " << mCreatorID << llendl;
}
@@ -275,28 +277,30 @@ LLEstateAssetRequest::~LLEstateAssetRequest()
// TODO: rework tempfile handling?
-LLAssetStorage::LLAssetStorage(LLMessageSystem *msg, LLXferManager *xfer, LLVFS *vfs, const LLHost &upstream_host)
+LLAssetStorage::LLAssetStorage(LLMessageSystem *msg, LLXferManager *xfer, LLVFS *vfs, LLVFS *static_vfs, const LLHost &upstream_host)
{
- _init(msg, xfer, vfs, upstream_host);
+ _init(msg, xfer, vfs, static_vfs, upstream_host);
}
LLAssetStorage::LLAssetStorage(LLMessageSystem *msg, LLXferManager *xfer,
- LLVFS *vfs)
+ LLVFS *vfs, LLVFS *static_vfs)
{
- _init(msg, xfer, vfs, LLHost::invalid);
+ _init(msg, xfer, vfs, static_vfs, LLHost::invalid);
}
void LLAssetStorage::_init(LLMessageSystem *msg,
LLXferManager *xfer,
LLVFS *vfs,
+ LLVFS *static_vfs,
const LLHost &upstream_host)
{
mShutDown = FALSE;
mMessageSys = msg;
mXferManager = xfer;
mVFS = vfs;
+ mStaticVFS = static_vfs;
setUpstream(upstream_host);
msg->setHandlerFuncFast(_PREHASH_AssetUploadComplete, processUploadComplete, (void **)this);
@@ -314,6 +318,9 @@ LLAssetStorage::~LLAssetStorage()
// unregister our callbacks with the message system
gMessageSystem->setHandlerFuncFast(_PREHASH_AssetUploadComplete, NULL, NULL);
}
+
+ // Clear the toxic asset map
+ mToxicAssetMap.clear();
}
void LLAssetStorage::setUpstream(const LLHost &upstream_host)
@@ -385,7 +392,33 @@ void LLAssetStorage::_cleanupRequests(BOOL all, S32 error)
BOOL LLAssetStorage::hasLocalAsset(const LLUUID &uuid, const LLAssetType::EType type)
{
- return mVFS->getExists(uuid, type);
+ return mStaticVFS->getExists(uuid, type) || mVFS->getExists(uuid, type);
+}
+
+bool LLAssetStorage::findInStaticVFSAndInvokeCallback(const LLUUID& uuid, LLAssetType::EType type,
+ LLGetAssetCallback callback, void *user_data)
+{
+ BOOL exists = mStaticVFS->getExists(uuid, type);
+ if (exists)
+ {
+ LLVFile file(mStaticVFS, uuid, type);
+ U32 size = file.getSize();
+ if (size > 0)
+ {
+ // we've already got the file
+ if (callback)
+ {
+ callback(mStaticVFS, uuid, type, user_data, LL_ERR_NOERR, LL_EXSTAT_VFS_CACHED);
+ }
+ return true;
+ }
+ else
+ {
+ llwarns << "Asset vfile " << uuid << ":" << type
+ << " found in static cache with bad size " << file.getSize() << ", ignoring" << llendl;
+ }
+ }
+ return false;
}
///////////////////////////////////////////////////////////////////////////
@@ -393,12 +426,15 @@ BOOL LLAssetStorage::hasLocalAsset(const LLUUID &uuid, const LLAssetType::EType
///////////////////////////////////////////////////////////////////////////
// IW - uuid is passed by value to avoid side effects, please don't re-add &
-void LLAssetStorage::getAssetData(const LLUUID uuid, LLAssetType::EType type, void (*callback)(LLVFS *vfs, const LLUUID&, LLAssetType::EType, void *, S32, LLExtStat), void *user_data, BOOL is_priority)
+void LLAssetStorage::getAssetData(const LLUUID uuid, LLAssetType::EType type, LLGetAssetCallback callback, void *user_data, BOOL is_priority)
{
lldebugs << "LLAssetStorage::getAssetData() - " << uuid << "," << LLAssetType::lookup(type) << llendl;
+ llinfos << "ASSET_TRACE requesting " << uuid << " type " << LLAssetType::lookup(type) << llendl;
+
if (mShutDown)
{
+ llinfos << "ASSET_TRACE cancelled " << uuid << " type " << LLAssetType::lookup(type) << " shutting down" << llendl;
return; // don't get the asset or do any callbacks, we are shutting down
}
@@ -412,11 +448,30 @@ void LLAssetStorage::getAssetData(const LLUUID uuid, LLAssetType::EType type, vo
return;
}
+ // Try static VFS first.
+ if (findInStaticVFSAndInvokeCallback(uuid,type,callback,user_data))
+ {
+ llinfos << "ASSET_TRACE asset " << uuid << " found in static VFS" << llendl;
+ return;
+ }
+
BOOL exists = mVFS->getExists(uuid, type);
LLVFile file(mVFS, uuid, type);
U32 size = exists ? file.getSize() : 0;
- if (size < 1)
+ if (size > 0)
+ {
+ // we've already got the file
+ // theoretically, partial files w/o a pending request shouldn't happen
+ // unless there's a weird error
+ if (callback)
+ {
+ callback(mVFS, uuid, type, user_data, LL_ERR_NOERR, LL_EXSTAT_VFS_CACHED);
+ }
+
+ llinfos << "ASSET_TRACE asset " << uuid << " found in VFS" << llendl;
+ }
+ else
{
if (exists)
{
@@ -455,16 +510,7 @@ void LLAssetStorage::getAssetData(const LLUUID uuid, LLAssetType::EType type, vo
// This can be overridden by subclasses
_queueDataRequest(uuid, type, callback, user_data, duplicate, is_priority);
}
- else
- {
- // we've already got the file
- // theoretically, partial files w/o a pending request shouldn't happen
- // unless there's a weird error
- if (callback)
- {
- callback(mVFS, uuid, type, user_data, LL_ERR_NOERR, LL_EXSTAT_VFS_CACHED);
- }
- }
+
}
void LLAssetStorage::_queueDataRequest(const LLUUID& uuid, LLAssetType::EType atype,
@@ -517,6 +563,8 @@ void LLAssetStorage::downloadCompleteCallback(
LLAssetType::EType file_type,
void* user_data, LLExtStat ext_status)
{
+ llinfos << "ASSET_TRACE asset " << file_id << " downloadCompleteCallback" << llendl;
+
lldebugs << "LLAssetStorage::downloadCompleteCallback() for " << file_id
<< "," << LLAssetType::lookup(file_type) << llendl;
LLAssetRequest* req = (LLAssetRequest*)user_data;
@@ -532,8 +580,19 @@ void LLAssetStorage::downloadCompleteCallback(
return;
}
- req->setUUID(file_id);
- req->setType(file_type);
+ // Inefficient since we're doing a find through a list that may have thousands of elements.
+ // This is due for refactoring; we will probably change mPendingDownloads into a set.
+ request_list_t::iterator download_iter = std::find(gAssetStorage->mPendingDownloads.begin(),
+ gAssetStorage->mPendingDownloads.end(),
+ req);
+ // If the LLAssetRequest doesn't exist in the downloads queue, then it either has already been deleted
+ // by _cleanupRequests, or it's a transfer.
+ if (download_iter != gAssetStorage->mPendingDownloads.end())
+ {
+ req->setUUID(file_id);
+ req->setType(file_type);
+ }
+
if (LL_ERR_NOERR == result)
{
// we might have gotten a zero-size file
@@ -556,7 +615,7 @@ void LLAssetStorage::downloadCompleteCallback(
{
request_list_t::iterator curiter = iter++;
LLAssetRequest* tmp = *curiter;
- if ((tmp->getUUID() == req->getUUID()) && (tmp->getType()== req->getType()))
+ if ((tmp->getUUID() == file_id) && (tmp->getType()== file_type))
{
requests.push_front(tmp);
iter = gAssetStorage->mPendingDownloads.erase(curiter);
@@ -594,11 +653,27 @@ void LLAssetStorage::getEstateAsset(const LLHost &object_sim, const LLUUID &agen
return;
}
+ // Try static VFS first.
+ if (findInStaticVFSAndInvokeCallback(asset_id,atype,callback,user_data))
+ {
+ return;
+ }
+
BOOL exists = mVFS->getExists(asset_id, atype);
LLVFile file(mVFS, asset_id, atype);
U32 size = exists ? file.getSize() : 0;
- if (size < 1)
+ if (size > 0)
+ {
+ // we've already got the file
+ // theoretically, partial files w/o a pending request shouldn't happen
+ // unless there's a weird error
+ if (callback)
+ {
+ callback(mVFS, asset_id, atype, user_data, LL_ERR_NOERR, LL_EXSTAT_VFS_CACHED);
+ }
+ }
+ else
{
if (exists)
{
@@ -649,16 +724,6 @@ void LLAssetStorage::getEstateAsset(const LLHost &object_sim, const LLUUID &agen
}
}
}
- else
- {
- // we've already got the file
- // theoretically, partial files w/o a pending request shouldn't happen
- // unless there's a weird error
- if (callback)
- {
- callback(mVFS, asset_id, atype, user_data, LL_ERR_NOERR, LL_EXSTAT_VFS_CACHED);
- }
- }
}
void LLAssetStorage::downloadEstateAssetCompleteCallback(
@@ -725,6 +790,12 @@ void LLAssetStorage::getInvItemAsset(const LLHost &object_sim, const LLUUID &age
if(asset_id.notNull())
{
+ // Try static VFS first.
+ if (findInStaticVFSAndInvokeCallback( asset_id, atype, callback, user_data))
+ {
+ return;
+ }
+
exists = mVFS->getExists(asset_id, atype);
LLVFile file(mVFS, asset_id, atype);
size = exists ? file.getSize() : 0;
@@ -736,7 +807,17 @@ void LLAssetStorage::getInvItemAsset(const LLHost &object_sim, const LLUUID &age
}
- if (size < 1)
+ if (size > 0)
+ {
+ // we've already got the file
+ // theoretically, partial files w/o a pending request shouldn't happen
+ // unless there's a weird error
+ if (callback)
+ {
+ callback(mVFS, asset_id, atype, user_data, LL_ERR_NOERR, LL_EXSTAT_VFS_CACHED);
+ }
+ }
+ else
{
// See whether we should talk to the object's originating sim,
// or the upstream provider.
@@ -785,16 +866,6 @@ void LLAssetStorage::getInvItemAsset(const LLHost &object_sim, const LLUUID &age
}
}
}
- else
- {
- // we've already got the file
- // theoretically, partial files w/o a pending request shouldn't happen
- // unless there's a weird error
- if (callback)
- {
- callback(mVFS, asset_id, atype, user_data, LL_ERR_NOERR, LL_EXSTAT_VFS_CACHED);
- }
- }
}
@@ -1006,12 +1077,12 @@ LLSD LLAssetStorage::getPendingDetails(LLAssetStorage::ERequestType rt,
{
const request_list_t* requests = getRequestList(rt);
LLSD sd;
- sd["requests"] = getPendingDetails(requests, asset_type, detail_prefix);
+ sd["requests"] = getPendingDetailsImpl(requests, asset_type, detail_prefix);
return sd;
}
// virtual
-LLSD LLAssetStorage::getPendingDetails(const LLAssetStorage::request_list_t* requests,
+LLSD LLAssetStorage::getPendingDetailsImpl(const LLAssetStorage::request_list_t* requests,
LLAssetType::EType asset_type,
const std::string& detail_prefix) const
{
@@ -1094,11 +1165,11 @@ LLSD LLAssetStorage::getPendingRequest(LLAssetStorage::ERequestType rt,
const LLUUID& asset_id) const
{
const request_list_t* requests = getRequestList(rt);
- return getPendingRequest(requests, asset_type, asset_id);
+ return getPendingRequestImpl(requests, asset_type, asset_id);
}
// virtual
-LLSD LLAssetStorage::getPendingRequest(const LLAssetStorage::request_list_t* requests,
+LLSD LLAssetStorage::getPendingRequestImpl(const LLAssetStorage::request_list_t* requests,
LLAssetType::EType asset_type,
const LLUUID& asset_id) const
{
@@ -1117,7 +1188,7 @@ bool LLAssetStorage::deletePendingRequest(LLAssetStorage::ERequestType rt,
const LLUUID& asset_id)
{
request_list_t* requests = getRequestList(rt);
- if (deletePendingRequest(requests, asset_type, asset_id))
+ if (deletePendingRequestImpl(requests, asset_type, asset_id))
{
llinfos << "Asset " << getRequestName(rt) << " request for "
<< asset_id << "." << LLAssetType::lookup(asset_type)
@@ -1128,7 +1199,7 @@ bool LLAssetStorage::deletePendingRequest(LLAssetStorage::ERequestType rt,
}
// virtual
-bool LLAssetStorage::deletePendingRequest(LLAssetStorage::request_list_t* requests,
+bool LLAssetStorage::deletePendingRequestImpl(LLAssetStorage::request_list_t* requests,
LLAssetType::EType asset_type,
const LLUUID& asset_id)
{
@@ -1191,6 +1262,9 @@ const char* LLAssetStorage::getErrorString(S32 status)
case LL_ERR_CIRCUIT_GONE:
return "Circuit gone";
+ case LL_ERR_PRICE_MISMATCH:
+ return "Viewer and server do not agree on price";
+
default:
return "Unknown status";
}
@@ -1231,16 +1305,20 @@ void LLAssetStorage::getAssetData(const LLUUID uuid, LLAssetType::EType type, vo
void LLAssetStorage::legacyGetDataCallback(LLVFS *vfs, const LLUUID &uuid, LLAssetType::EType type, void *user_data, S32 status, LLExtStat ext_status)
{
LLLegacyAssetRequest *legacy = (LLLegacyAssetRequest *)user_data;
- char filename[LL_MAX_PATH] = ""; /* Flawfinder: ignore */
+ std::string filename;
- if (! status)
+ // Check if the asset is marked toxic, and don't load bad stuff
+ BOOL toxic = gAssetStorage->isAssetToxic( uuid );
+
+ if ( !status
+ && !toxic )
{
LLVFile file(vfs, uuid, type);
- char uuid_str[UUID_STR_LENGTH]; /* Flawfinder: ignore */
+ std::string uuid_str;
uuid.toString(uuid_str);
- snprintf(filename,sizeof(filename),"%s.%s",gDirUtilp->getExpandedFilename(LL_PATH_CACHE,uuid_str).c_str(),LLAssetType::lookup(type)); /* Flawfinder: ignore */
+ filename = llformat("%s.%s",gDirUtilp->getExpandedFilename(LL_PATH_CACHE,uuid_str).c_str(),LLAssetType::lookup(type));
LLFILE* fp = LLFile::fopen(filename, "wb"); /* Flawfinder: ignore */
if (fp)
@@ -1264,7 +1342,7 @@ void LLAssetStorage::legacyGetDataCallback(LLVFS *vfs, const LLUUID &uuid, LLAss
}
}
- legacy->mDownCallback(filename, uuid, legacy->mUserData, status, ext_status);
+ legacy->mDownCallback(filename.c_str(), uuid, legacy->mUserData, status, ext_status);
delete legacy;
}
@@ -1283,7 +1361,7 @@ void LLAssetStorage::storeAssetData(
{
llwarns << "storeAssetData: wrong version called" << llendl;
// LLAssetStorage metric: Virtual base call
- reportMetric( LLUUID::null, asset_type, NULL, LLUUID::null, 0, MR_BAD_FUNCTION, __FILE__, __LINE__, "Illegal call to base: LLAssetStorage::storeAssetData 1" );
+ reportMetric( LLUUID::null, asset_type, LLStringUtil::null, LLUUID::null, 0, MR_BAD_FUNCTION, __FILE__, __LINE__, "Illegal call to base: LLAssetStorage::storeAssetData 1" );
}
// virtual
@@ -1302,13 +1380,13 @@ void LLAssetStorage::storeAssetData(
{
llwarns << "storeAssetData: wrong version called" << llendl;
// LLAssetStorage metric: Virtual base call
- reportMetric( asset_id, asset_type, NULL, requesting_agent_id, 0, MR_BAD_FUNCTION, __FILE__, __LINE__, "Illegal call to base: LLAssetStorage::storeAssetData 2" );
+ reportMetric( asset_id, asset_type, LLStringUtil::null, requesting_agent_id, 0, MR_BAD_FUNCTION, __FILE__, __LINE__, "Illegal call to base: LLAssetStorage::storeAssetData 2" );
}
// virtual
// this does nothing, viewer and sim both override this.
void LLAssetStorage::storeAssetData(
- const char* filename,
+ const std::string& filename,
const LLUUID& asset_id,
LLAssetType::EType asset_type,
LLStoreAssetCallback callback,
@@ -1320,13 +1398,13 @@ void LLAssetStorage::storeAssetData(
{
llwarns << "storeAssetData: wrong version called" << llendl;
// LLAssetStorage metric: Virtual base call
- reportMetric( asset_id, asset_type, NULL, LLUUID::null, 0, MR_BAD_FUNCTION, __FILE__, __LINE__, "Illegal call to base: LLAssetStorage::storeAssetData 3" );
+ reportMetric( asset_id, asset_type, LLStringUtil::null, LLUUID::null, 0, MR_BAD_FUNCTION, __FILE__, __LINE__, "Illegal call to base: LLAssetStorage::storeAssetData 3" );
}
// virtual
// this does nothing, viewer and sim both override this.
void LLAssetStorage::storeAssetData(
- const char* filename,
+ const std::string& filename,
const LLTransactionID &transactoin_id,
LLAssetType::EType asset_type,
LLStoreAssetCallback callback,
@@ -1338,7 +1416,7 @@ void LLAssetStorage::storeAssetData(
{
llwarns << "storeAssetData: wrong version called" << llendl;
// LLAssetStorage metric: Virtual base call
- reportMetric( LLUUID::null, asset_type, NULL, LLUUID::null, 0, MR_BAD_FUNCTION, __FILE__, __LINE__, "Illegal call to base: LLAssetStorage::storeAssetData 4" );
+ reportMetric( LLUUID::null, asset_type, LLStringUtil::null, LLUUID::null, 0, MR_BAD_FUNCTION, __FILE__, __LINE__, "Illegal call to base: LLAssetStorage::storeAssetData 4" );
}
// static
@@ -1385,9 +1463,9 @@ void LLAssetStorage::clearTempAssetData()
{ }
// static
-void LLAssetStorage::reportMetric( const LLUUID& asset_id, const LLAssetType::EType asset_type, const char *filename,
+void LLAssetStorage::reportMetric( const LLUUID& asset_id, const LLAssetType::EType asset_type, const std::string& in_filename,
const LLUUID& agent_id, S32 asset_size, EMetricResult result,
- const char *file, const S32 line, const char *message )
+ const char *file, const S32 line, const std::string& in_message )
{
if( !metric_recipient )
{
@@ -1395,18 +1473,13 @@ void LLAssetStorage::reportMetric( const LLUUID& asset_id, const LLAssetType::ET
return;
}
- filename = filename ? filename : "";
- file = file ? file : "";
-
- // Create revised message - message = "message :: file:line"
- std::string new_message; //( message );
- new_message = message; // << " " << file << " " << line;
- new_message += " :: ";
- new_message += filename;
- char line_string[16];
- sprintf( line_string, ":%d", line );
- new_message += line_string;
- message = new_message.c_str();
+ std::string filename(in_filename);
+ if (filename.empty())
+ filename = ll_safe_string(file);
+
+ // Create revised message - new_message = "in_message :: file:line"
+ std::stringstream new_message;
+ new_message << in_message << " :: " << filename << ":" << line;
// Change always_report to true if debugging... do not check it in this way
static bool always_report = false;
@@ -1419,15 +1492,68 @@ void LLAssetStorage::reportMetric( const LLUUID& asset_id, const LLAssetType::ET
LLSD stats;
stats["asset_id"] = asset_id;
stats["asset_type"] = asset_type;
- stats["filename"] = filename? filename : "";
+ stats["filename"] = filename;
stats["agent_id"] = agent_id;
stats["asset_size"] = (S32)asset_size;
stats["result"] = (S32)result;
- metric_recipient->recordEventDetails( metric_name, message, success, stats);
+ metric_recipient->recordEventDetails( metric_name, new_message.str(), success, stats);
}
else
{
- metric_recipient->recordEvent(metric_name, message, success);
+ metric_recipient->recordEvent(metric_name, new_message.str(), success);
}
}
+
+
+// Check if an asset is in the toxic map. If it is, the entry is updated
+BOOL LLAssetStorage::isAssetToxic( const LLUUID& uuid )
+{
+ BOOL is_toxic = FALSE;
+
+ if ( !uuid.isNull() )
+ {
+ toxic_asset_map_t::iterator iter = mToxicAssetMap.find( uuid );
+ if ( iter != mToxicAssetMap.end() )
+ { // Found toxic asset
+ (*iter).second = LLFrameTimer::getTotalTime() + TOXIC_ASSET_LIFETIME;
+ is_toxic = TRUE;
+ }
+ }
+ return is_toxic;
+}
+
+
+
+
+// Clean the toxic asset list, remove old entries
+void LLAssetStorage::flushOldToxicAssets( BOOL force_it )
+{
+ // Scan and look for old entries
+ U64 now = LLFrameTimer::getTotalTime();
+ toxic_asset_map_t::iterator iter = mToxicAssetMap.begin();
+ while ( iter != mToxicAssetMap.end() )
+ {
+ if ( force_it
+ || (*iter).second < now )
+ { // Too old - remove it
+ mToxicAssetMap.erase( iter++ );
+ }
+ else
+ {
+ iter++;
+ }
+ }
+}
+
+
+// Add an item to the toxic asset map
+void LLAssetStorage::markAssetToxic( const LLUUID& uuid )
+{
+ if ( !uuid.isNull() )
+ {
+ // Set the value to the current time. Creates a new entry if needed
+ mToxicAssetMap[ uuid ] = LLFrameTimer::getTotalTime() + TOXIC_ASSET_LIFETIME;
+ }
+}
+