virtual int get_load_priority() const { return 0; }
virtual AsyncLoader *load(IO::Seekable &, const Resources * = 0) = 0;
virtual bool is_loaded() const;
+
+ /** Returns the amount of graphics memory used by this resource. The
+ returned value must not change while the resource is loaded. */
virtual UInt64 get_data_size() const = 0;
+
virtual void unload() = 0;
};
managed.start_loading();
while(!managed.loader->process()) ;
managed.finish_loading(true);
+ total_data_size += managed.data_size;
}
}
bool do_unload = (frame>=next_unload);
if(thread.sync())
+ {
+ total_data_size += thread.get_and_reset_loaded_data_size();
do_unload = true;
+ }
if(thread.needs_work() && !queue.empty())
dispatch_work();
for(ResourceMap::iterator i=resources.begin(); i!=resources.end(); ++i)
if(i->second.state==ManagedResource::LOADED && i->second.last_used<unload_limit)
+ {
i->second.unload();
+ total_data_size -= i->second.data_size;
+ }
}
void ResourceManager::unload_by_size()
{
unsigned unload_limit = frame-min_retain_frames;
- while(get_total_data_size_()>size_limit)
+ while(total_data_size>size_limit)
{
ManagedResource *best = 0;
UInt64 best_impact = 0;
break;
best->unload();
+ total_data_size -= best->data_size;
}
}
-UInt64 ResourceManager::get_total_data_size_() const
-{
- UInt64 total = 0;
- for(ResourceMap::const_iterator i=resources.begin(); i!=resources.end(); ++i)
- if(i->second.state==ManagedResource::LOADED)
- total += i->second.data_size;
- return total;
-}
-
-UInt64 ResourceManager::get_total_data_size() const
-{
- MutexLock lock(map_mutex);
- return get_total_data_size_();
-}
-
bool ResourceManager::age_order(ManagedResource *mr1, ManagedResource *mr2)
{
return mr1->last_used>mr2->last_used;
Time::sleep(Time::msec);
r.finish_loading();
+ if(r.state==ManagedResource::LOADED)
+ {
+ MutexLock lock(data_size_mutex);
+ loaded_data_size += r.data_size;
+ }
}
bool ResourceManager::LoadingThread::try_remove_resource(ManagedResource &r)
if(managed->state==ManagedResource::LOAD_ERROR || managed->process(true))
{
managed->finish_loading();
+ if(managed->state==ManagedResource::LOADED)
+ {
+ MutexLock lock(data_size_mutex);
+ loaded_data_size += managed->data_size;
+ }
any_finished = true;
--size;
return any_finished;
}
+UInt64 ResourceManager::LoadingThread::get_and_reset_loaded_data_size()
+{
+ MutexLock lock(data_size_mutex);
+ UInt64 result = loaded_data_size;
+ loaded_data_size = 0;
+ return result;
+}
+
void ResourceManager::LoadingThread::terminate()
{
done = true;
unsigned capacity;
unsigned size;
std::list<resource_load_error> error_queue;
+ Mutex data_size_mutex;
+ UInt64 loaded_data_size;
volatile bool done;
public:
public:
bool sync();
bool needs_work() const { return size<capacity; }
+ UInt64 get_and_reset_loaded_data_size();
void terminate();
};
mutable Mutex map_mutex;
ResourceMap resources;
LoadQueue queue;
+ UInt64 total_data_size;
UInt64 size_limit;
unsigned frame;
unsigned min_retain_frames;
void dispatch_work();
void unload_by_age();
void unload_by_size();
- UInt64 get_total_data_size_() const;
public:
- UInt64 get_total_data_size() const;
+ UInt64 get_total_data_size() const { return total_data_size; }
private:
static bool age_order(ManagedResource *, ManagedResource *);