mirror of https://github.com/aria2/aria2
Save session only when there is change since the last serialization
This is a slight optimization not to cause useless disk access. This only applies to saving session automatically (see --save-session-interval). aria2.saveSession and serialization at the end of the session are always performed as before.pull/235/merge
parent
8ada3283f2
commit
1944d8db58
|
@ -111,6 +111,7 @@ RequestGroupMan::RequestGroupMan
|
||||||
(PREF_MAX_OVERALL_UPLOAD_LIMIT)),
|
(PREF_MAX_OVERALL_UPLOAD_LIMIT)),
|
||||||
keepRunning_(option->getAsBool(PREF_ENABLE_RPC)),
|
keepRunning_(option->getAsBool(PREF_ENABLE_RPC)),
|
||||||
queueCheck_(true),
|
queueCheck_(true),
|
||||||
|
requireSaveSession_(false),
|
||||||
removedErrorResult_(0),
|
removedErrorResult_(0),
|
||||||
removedLastErrorResult_(error_code::FINISHED),
|
removedLastErrorResult_(error_code::FINISHED),
|
||||||
maxDownloadResult_(option->getAsInt(PREF_MAX_DOWNLOAD_RESULT)),
|
maxDownloadResult_(option->getAsInt(PREF_MAX_DOWNLOAD_RESULT)),
|
||||||
|
@ -120,6 +121,9 @@ RequestGroupMan::RequestGroupMan
|
||||||
{
|
{
|
||||||
appendReservedGroup(reservedGroups_,
|
appendReservedGroup(reservedGroups_,
|
||||||
requestGroups.begin(), requestGroups.end());
|
requestGroups.begin(), requestGroups.end());
|
||||||
|
if(!reservedGroups_.empty()) {
|
||||||
|
requireSaveSession_ = true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
RequestGroupMan::~RequestGroupMan()
|
RequestGroupMan::~RequestGroupMan()
|
||||||
|
@ -139,6 +143,7 @@ void RequestGroupMan::addRequestGroup
|
||||||
(const std::shared_ptr<RequestGroup>& group)
|
(const std::shared_ptr<RequestGroup>& group)
|
||||||
{
|
{
|
||||||
requestGroups_.push_back(group->getGID(), group);
|
requestGroups_.push_back(group->getGID(), group);
|
||||||
|
requireSaveSession_ = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void RequestGroupMan::addReservedGroup
|
void RequestGroupMan::addReservedGroup
|
||||||
|
@ -146,6 +151,9 @@ void RequestGroupMan::addReservedGroup
|
||||||
{
|
{
|
||||||
requestQueueCheck();
|
requestQueueCheck();
|
||||||
appendReservedGroup(reservedGroups_, groups.begin(), groups.end());
|
appendReservedGroup(reservedGroups_, groups.begin(), groups.end());
|
||||||
|
if(!reservedGroups_.empty()) {
|
||||||
|
requireSaveSession_ = true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void RequestGroupMan::addReservedGroup
|
void RequestGroupMan::addReservedGroup
|
||||||
|
@ -153,6 +161,7 @@ void RequestGroupMan::addReservedGroup
|
||||||
{
|
{
|
||||||
requestQueueCheck();
|
requestQueueCheck();
|
||||||
reservedGroups_.push_back(group->getGID(), group);
|
reservedGroups_.push_back(group->getGID(), group);
|
||||||
|
requireSaveSession_ = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
@ -171,6 +180,7 @@ void RequestGroupMan::insertReservedGroup
|
||||||
pos = std::min(reservedGroups_.size(), pos);
|
pos = std::min(reservedGroups_.size(), pos);
|
||||||
reservedGroups_.insert(pos, RequestGroupKeyFunc(),
|
reservedGroups_.insert(pos, RequestGroupKeyFunc(),
|
||||||
groups.begin(), groups.end());
|
groups.begin(), groups.end());
|
||||||
|
requireSaveSession_ = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void RequestGroupMan::insertReservedGroup
|
void RequestGroupMan::insertReservedGroup
|
||||||
|
@ -179,6 +189,7 @@ void RequestGroupMan::insertReservedGroup
|
||||||
requestQueueCheck();
|
requestQueueCheck();
|
||||||
pos = std::min(reservedGroups_.size(), pos);
|
pos = std::min(reservedGroups_.size(), pos);
|
||||||
reservedGroups_.insert(pos, group->getGID(), group);
|
reservedGroups_.insert(pos, group->getGID(), group);
|
||||||
|
requireSaveSession_ = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t RequestGroupMan::countRequestGroup() const
|
size_t RequestGroupMan::countRequestGroup() const
|
||||||
|
@ -202,13 +213,16 @@ size_t RequestGroupMan::changeReservedGroupPosition
|
||||||
if(dest == -1) {
|
if(dest == -1) {
|
||||||
throw DL_ABORT_EX(fmt("GID#%s not found in the waiting queue.",
|
throw DL_ABORT_EX(fmt("GID#%s not found in the waiting queue.",
|
||||||
GroupId::toHex(gid).c_str()));
|
GroupId::toHex(gid).c_str()));
|
||||||
} else {
|
|
||||||
return dest;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
requireSaveSession_ = true;
|
||||||
|
|
||||||
|
return dest;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool RequestGroupMan::removeReservedGroup(a2_gid_t gid)
|
bool RequestGroupMan::removeReservedGroup(a2_gid_t gid)
|
||||||
{
|
{
|
||||||
|
requireSaveSession_ = true;
|
||||||
return reservedGroups_.remove(gid);
|
return reservedGroups_.remove(gid);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -387,6 +401,7 @@ public:
|
||||||
} catch(RecoverableException& ex) {
|
} catch(RecoverableException& ex) {
|
||||||
A2_LOG_ERROR_EX(EX_EXCEPTION_CAUGHT, ex);
|
A2_LOG_ERROR_EX(EX_EXCEPTION_CAUGHT, ex);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(group->isPauseRequested()) {
|
if(group->isPauseRequested()) {
|
||||||
group->setState(RequestGroup::STATE_WAITING);
|
group->setState(RequestGroup::STATE_WAITING);
|
||||||
reservedGroups_.push_front(group->getGID(), group);
|
reservedGroups_.push_front(group->getGID(), group);
|
||||||
|
@ -417,6 +432,7 @@ void RequestGroupMan::removeStoppedGroup(DownloadEngine* e)
|
||||||
requestGroups_.remove_if(ProcessStoppedRequestGroup(e, reservedGroups_));
|
requestGroups_.remove_if(ProcessStoppedRequestGroup(e, reservedGroups_));
|
||||||
size_t numRemoved = numPrev-requestGroups_.size();
|
size_t numRemoved = numPrev-requestGroups_.size();
|
||||||
if(numRemoved > 0) {
|
if(numRemoved > 0) {
|
||||||
|
requireSaveSession_ = true;
|
||||||
A2_LOG_DEBUG(fmt("%lu RequestGroup(s) deleted.",
|
A2_LOG_DEBUG(fmt("%lu RequestGroup(s) deleted.",
|
||||||
static_cast<unsigned long>(numRemoved)));
|
static_cast<unsigned long>(numRemoved)));
|
||||||
}
|
}
|
||||||
|
@ -466,6 +482,7 @@ void RequestGroupMan::fillRequestGroupFromReserver(DownloadEngine* e)
|
||||||
uriListParser_.get());
|
uriListParser_.get());
|
||||||
if(ok) {
|
if(ok) {
|
||||||
appendReservedGroup(reservedGroups_, groups.begin(), groups.end());
|
appendReservedGroup(reservedGroups_, groups.begin(), groups.end());
|
||||||
|
requireSaveSession_ = true;
|
||||||
} else {
|
} else {
|
||||||
uriListParser_.reset();
|
uriListParser_.reset();
|
||||||
if(reservedGroups_.empty()) {
|
if(reservedGroups_.empty()) {
|
||||||
|
@ -487,6 +504,7 @@ void RequestGroupMan::fillRequestGroupFromReserver(DownloadEngine* e)
|
||||||
groupToAdd->setRequestGroupMan(this);
|
groupToAdd->setRequestGroupMan(this);
|
||||||
groupToAdd->setState(RequestGroup::STATE_ACTIVE);
|
groupToAdd->setState(RequestGroup::STATE_ACTIVE);
|
||||||
requestGroups_.push_back(groupToAdd->getGID(), groupToAdd);
|
requestGroups_.push_back(groupToAdd->getGID(), groupToAdd);
|
||||||
|
requireSaveSession_ = true;
|
||||||
try {
|
try {
|
||||||
auto res = createInitialCommand(groupToAdd, e);
|
auto res = createInitialCommand(groupToAdd, e);
|
||||||
++count;
|
++count;
|
||||||
|
@ -828,6 +846,7 @@ RequestGroupMan::findDownloadResult(a2_gid_t gid) const
|
||||||
|
|
||||||
bool RequestGroupMan::removeDownloadResult(a2_gid_t gid)
|
bool RequestGroupMan::removeDownloadResult(a2_gid_t gid)
|
||||||
{
|
{
|
||||||
|
requireSaveSession_ = true;
|
||||||
return downloadResults_.remove(gid);
|
return downloadResults_.remove(gid);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -836,6 +855,7 @@ void RequestGroupMan::addDownloadResult(const std::shared_ptr<DownloadResult>& d
|
||||||
++numStoppedTotal_;
|
++numStoppedTotal_;
|
||||||
bool rv = downloadResults_.push_back(dr->gid->getNumericId(), dr);
|
bool rv = downloadResults_.push_back(dr->gid->getNumericId(), dr);
|
||||||
assert(rv);
|
assert(rv);
|
||||||
|
requireSaveSession_ = true;
|
||||||
while(downloadResults_.size() > maxDownloadResult_){
|
while(downloadResults_.size() > maxDownloadResult_){
|
||||||
DownloadResultList::iterator i = downloadResults_.begin();
|
DownloadResultList::iterator i = downloadResults_.begin();
|
||||||
// Save last encountered error code so that we can report it
|
// Save last encountered error code so that we can report it
|
||||||
|
@ -851,6 +871,7 @@ void RequestGroupMan::addDownloadResult(const std::shared_ptr<DownloadResult>& d
|
||||||
|
|
||||||
void RequestGroupMan::purgeDownloadResult()
|
void RequestGroupMan::purgeDownloadResult()
|
||||||
{
|
{
|
||||||
|
requireSaveSession_ = true;
|
||||||
downloadResults_.clear();
|
downloadResults_.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -90,6 +90,11 @@ private:
|
||||||
|
|
||||||
bool queueCheck_;
|
bool queueCheck_;
|
||||||
|
|
||||||
|
// true if there is a change in at least one of requestGroups_,
|
||||||
|
// reservedGroups_ and downloadResults_ since the last session
|
||||||
|
// serialization, so we need to save session file next time.
|
||||||
|
bool requireSaveSession_;
|
||||||
|
|
||||||
// The number of error DownloadResult removed because of upper limit
|
// The number of error DownloadResult removed because of upper limit
|
||||||
// of the queue
|
// of the queue
|
||||||
int removedErrorResult_;
|
int removedErrorResult_;
|
||||||
|
@ -368,6 +373,16 @@ public:
|
||||||
{
|
{
|
||||||
return numStoppedTotal_;
|
return numStoppedTotal_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool getRequireSaveSession() const
|
||||||
|
{
|
||||||
|
return requireSaveSession_;
|
||||||
|
}
|
||||||
|
|
||||||
|
void clearRequireSaveSession()
|
||||||
|
{
|
||||||
|
requireSaveSession_ = false;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace aria2
|
} // namespace aria2
|
||||||
|
|
|
@ -60,12 +60,23 @@ void SaveSessionCommand::preProcess()
|
||||||
|
|
||||||
void SaveSessionCommand::process()
|
void SaveSessionCommand::process()
|
||||||
{
|
{
|
||||||
|
auto& rgman = getDownloadEngine()->getRequestGroupMan();
|
||||||
|
|
||||||
|
if(!rgman->getRequireSaveSession()) {
|
||||||
|
A2_LOG_INFO("No change in queues since last serialization or startup. "
|
||||||
|
"No serialization is necessary this time.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
const std::string& filename = getDownloadEngine()->getOption()
|
const std::string& filename = getDownloadEngine()->getOption()
|
||||||
->get(PREF_SAVE_SESSION);
|
->get(PREF_SAVE_SESSION);
|
||||||
|
|
||||||
if(!filename.empty()) {
|
if(!filename.empty()) {
|
||||||
SessionSerializer sessionSerializer(getDownloadEngine()->
|
SessionSerializer sessionSerializer(rgman.get());
|
||||||
getRequestGroupMan().get());
|
|
||||||
if(sessionSerializer.save(filename)) {
|
if(sessionSerializer.save(filename)) {
|
||||||
|
rgman->clearRequireSaveSession();
|
||||||
|
|
||||||
A2_LOG_NOTICE(fmt(_("Serialized session to '%s' successfully."),
|
A2_LOG_NOTICE(fmt(_("Serialized session to '%s' successfully."),
|
||||||
filename.c_str()));
|
filename.c_str()));
|
||||||
} else {
|
} else {
|
||||||
|
|
Loading…
Reference in New Issue