diff options
-rw-r--r-- | ChangeLog.txt | 7 | ||||
-rw-r--r-- | linden/indra/newview/lltexturecache.cpp | 65 | ||||
-rw-r--r-- | linden/indra/newview/lltexturecache.h | 5 |
3 files changed, 71 insertions, 6 deletions
diff --git a/ChangeLog.txt b/ChangeLog.txt index e69de29..da78f78 100644 --- a/ChangeLog.txt +++ b/ChangeLog.txt | |||
@@ -0,0 +1,7 @@ | |||
1 | 2008-09-16 Nicholaz Beresford <nicholaz@blueflash.cc> | ||
2 | |||
3 | * linden/indra/newview/lltexturecache.cpp: | ||
4 | VWR-3878: Purging cache textures causes viewer to pause for many | ||
5 | seconds, with heavy disk activity. | ||
6 | * linden/indra/newview/lltexturecache.h: | ||
7 | Ditto. | ||
diff --git a/linden/indra/newview/lltexturecache.cpp b/linden/indra/newview/lltexturecache.cpp index 22cb6c1..0fbb3d9 100644 --- a/linden/indra/newview/lltexturecache.cpp +++ b/linden/indra/newview/lltexturecache.cpp | |||
@@ -881,6 +881,8 @@ LLTextureCache::LLTextureCache(bool threaded) | |||
881 | 881 | ||
882 | LLTextureCache::~LLTextureCache() | 882 | LLTextureCache::~LLTextureCache() |
883 | { | 883 | { |
884 | purgeTextureFilesTimeSliced(TRUE); // force-flush all pending file deletes | ||
885 | |||
884 | apr_pool_destroy(mFileAPRPool); | 886 | apr_pool_destroy(mFileAPRPool); |
885 | } | 887 | } |
886 | 888 | ||
@@ -1187,7 +1189,7 @@ void LLTextureCache::purgeTextures(bool validate) | |||
1187 | return; | 1189 | return; |
1188 | } | 1190 | } |
1189 | 1191 | ||
1190 | LL_DEBUGS("TextureCache") << "TEXTURE CACHE: Reading Entries..." << LL_ENDL; | 1192 | LL_DEBUGS("TextureCache") << "TEXTURE CACHE: Reading " << num_entries << " Entries from " << mTexturesDirEntriesFileName << LL_ENDL; |
1191 | 1193 | ||
1192 | std::map<LLUUID, S32> entry_idx_map; | 1194 | std::map<LLUUID, S32> entry_idx_map; |
1193 | S64 total_size = 0; | 1195 | S64 total_size = 0; |
@@ -1216,7 +1218,7 @@ void LLTextureCache::purgeTextures(bool validate) | |||
1216 | LL_DEBUGS("TextureCache") << "TEXTURE CACHE: Validating: " << validate_idx << LL_ENDL; | 1218 | LL_DEBUGS("TextureCache") << "TEXTURE CACHE: Validating: " << validate_idx << LL_ENDL; |
1217 | } | 1219 | } |
1218 | 1220 | ||
1219 | S64 min_cache_size = (sCacheMaxTexturesSize * 9) / 10; | 1221 | S64 min_cache_size = sCacheMaxTexturesSize / 100 * 95; |
1220 | S32 purge_count = 0; | 1222 | S32 purge_count = 0; |
1221 | S32 next_idx = 0; | 1223 | S32 next_idx = 0; |
1222 | for (S32 idx=0; idx<num_entries; idx++) | 1224 | for (S32 idx=0; idx<num_entries; idx++) |
@@ -1250,8 +1252,8 @@ void LLTextureCache::purgeTextures(bool validate) | |||
1250 | if (purge_entry) | 1252 | if (purge_entry) |
1251 | { | 1253 | { |
1252 | purge_count++; | 1254 | purge_count++; |
1253 | LL_DEBUGS("TextureCache") << "PURGING: " << filename << LL_ENDL; | 1255 | LL_DEBUGS("TextureCache") << "PURGING: " << filename << LL_ENDL; |
1254 | ll_apr_file_remove(filename, NULL); | 1256 | mFilesToDelete.push_back(filename); |
1255 | total_size -= entries[idx].mSize; | 1257 | total_size -= entries[idx].mSize; |
1256 | entries[idx].mSize = 0; | 1258 | entries[idx].mSize = 0; |
1257 | } | 1259 | } |
@@ -1266,7 +1268,11 @@ void LLTextureCache::purgeTextures(bool validate) | |||
1266 | } | 1268 | } |
1267 | num_entries = next_idx; | 1269 | num_entries = next_idx; |
1268 | 1270 | ||
1269 | LL_DEBUGS("TextureCache") << "TEXTURE CACHE: Writing Entries: " << num_entries << LL_ENDL; | 1271 | mTimeLastFileDelete.reset(); |
1272 | |||
1273 | LL_DEBUGS("TextureCache") << "TEXTURE CACHE: Writing Entries: " | ||
1274 | << num_entries << " (" << num_entries*sizeof(Entry)/1024 << "KB)" | ||
1275 | << LL_ENDL; | ||
1270 | 1276 | ||
1271 | ll_apr_file_remove(mTexturesDirEntriesFileName, NULL); | 1277 | ll_apr_file_remove(mTexturesDirEntriesFileName, NULL); |
1272 | ll_apr_file_write_ex(mTexturesDirEntriesFileName, NULL, | 1278 | ll_apr_file_write_ex(mTexturesDirEntriesFileName, NULL, |
@@ -1289,10 +1295,53 @@ void LLTextureCache::purgeTextures(bool validate) | |||
1289 | LL_INFOS("TextureCache") << "TEXTURE CACHE:" | 1295 | LL_INFOS("TextureCache") << "TEXTURE CACHE:" |
1290 | << " PURGED: " << purge_count | 1296 | << " PURGED: " << purge_count |
1291 | << " ENTRIES: " << num_entries | 1297 | << " ENTRIES: " << num_entries |
1292 | << " CACHE SIZE: " << total_size / 1024*1024 << " MB" | 1298 | << " CACHE SIZE: " << total_size/1024/1024 << " MB" |
1293 | << llendl; | 1299 | << llendl; |
1294 | } | 1300 | } |
1295 | 1301 | ||
1302 | |||
1303 | void LLTextureCache::purgeTextureFilesTimeSliced(BOOL force_all) | ||
1304 | { | ||
1305 | LLMutexLock lock(&mHeaderMutex); | ||
1306 | |||
1307 | F32 delay_between_passes = 1.0f; // seconds | ||
1308 | F32 max_time_per_pass = 0.1f; // seconds | ||
1309 | |||
1310 | if (!force_all && mTimeLastFileDelete.getElapsedTimeF32() <= delay_between_passes) | ||
1311 | { | ||
1312 | return; | ||
1313 | } | ||
1314 | |||
1315 | LLTimer timer; | ||
1316 | S32 howmany = 0; | ||
1317 | |||
1318 | llinfos << "TEXTURE CACHE: " << mFilesToDelete.size() << " files scheduled for deletion" << llendl; | ||
1319 | |||
1320 | for (LLTextureCache::filename_list_t::iterator iter = mFilesToDelete.begin(); iter!=mFilesToDelete.end(); ) | ||
1321 | { | ||
1322 | LLTextureCache::filename_list_t::iterator iter2 = iter++; | ||
1323 | ll_apr_file_remove(*iter2, NULL); | ||
1324 | mFilesToDelete.erase(iter2); | ||
1325 | howmany++; | ||
1326 | |||
1327 | if (!force_all && timer.getElapsedTimeF32() > max_time_per_pass) | ||
1328 | { | ||
1329 | break; | ||
1330 | } | ||
1331 | } | ||
1332 | |||
1333 | if (!mFilesToDelete.empty()) | ||
1334 | { | ||
1335 | llinfos << "TEXTURE CACHE: "<< howmany << " files deleted (" | ||
1336 | << mFilesToDelete.size() << " files left for next pass)" | ||
1337 | << llendl; | ||
1338 | } | ||
1339 | |||
1340 | mTimeLastFileDelete.reset(); | ||
1341 | } | ||
1342 | |||
1343 | |||
1344 | |||
1296 | ////////////////////////////////////////////////////////////////////////////// | 1345 | ////////////////////////////////////////////////////////////////////////////// |
1297 | 1346 | ||
1298 | // call lockWorkers() first! | 1347 | // call lockWorkers() first! |
@@ -1462,6 +1511,10 @@ LLTextureCache::handle_t LLTextureCache::writeToCache(const LLUUID& id, U32 prio | |||
1462 | purgeTextures(false); | 1511 | purgeTextures(false); |
1463 | mDoPurge = FALSE; | 1512 | mDoPurge = FALSE; |
1464 | } | 1513 | } |
1514 | |||
1515 | purgeTextureFilesTimeSliced(); // purge textures from cache in a non-hiccup-way | ||
1516 | |||
1517 | |||
1465 | if (datasize >= TEXTURE_CACHE_ENTRY_SIZE) | 1518 | if (datasize >= TEXTURE_CACHE_ENTRY_SIZE) |
1466 | { | 1519 | { |
1467 | LLMutexLock lock(&mWorkersMutex); | 1520 | LLMutexLock lock(&mWorkersMutex); |
diff --git a/linden/indra/newview/lltexturecache.h b/linden/indra/newview/lltexturecache.h index f083dd0..e15a88b 100644 --- a/linden/indra/newview/lltexturecache.h +++ b/linden/indra/newview/lltexturecache.h | |||
@@ -119,6 +119,7 @@ private: | |||
119 | void readHeaderCache(apr_pool_t* poolp = NULL); | 119 | void readHeaderCache(apr_pool_t* poolp = NULL); |
120 | void purgeAllTextures(bool purge_directories); | 120 | void purgeAllTextures(bool purge_directories); |
121 | void purgeTextures(bool validate); | 121 | void purgeTextures(bool validate); |
122 | void purgeTextureFilesTimeSliced(BOOL force_all = FALSE); | ||
122 | S32 getHeaderCacheEntry(const LLUUID& id, bool touch, S32* imagesize = NULL); | 123 | S32 getHeaderCacheEntry(const LLUUID& id, bool touch, S32* imagesize = NULL); |
123 | bool removeHeaderCacheEntry(const LLUUID& id); | 124 | bool removeHeaderCacheEntry(const LLUUID& id); |
124 | void lockHeaders() { mHeaderMutex.lock(); } | 125 | void lockHeaders() { mHeaderMutex.lock(); } |
@@ -140,6 +141,10 @@ private: | |||
140 | 141 | ||
141 | typedef std::vector<std::pair<LLPointer<Responder>, bool> > responder_list_t; | 142 | typedef std::vector<std::pair<LLPointer<Responder>, bool> > responder_list_t; |
142 | responder_list_t mCompletedList; | 143 | responder_list_t mCompletedList; |
144 | |||
145 | typedef std::list<std::string> filename_list_t; | ||
146 | filename_list_t mFilesToDelete; | ||
147 | LLTimer mTimeLastFileDelete; | ||
143 | 148 | ||
144 | BOOL mReadOnly; | 149 | BOOL mReadOnly; |
145 | 150 | ||