Copy-from-install support in TerraSync
Allows repositories to be initialised based on data in the install. This avoids duplicate downloading of the Model and Airport data, and the starting scenery. Requires a corresponding FlightGear change to be functional.
This commit is contained in:
@@ -150,6 +150,7 @@ public:
|
||||
typedef std::vector<HTTPDirectory*> DirectoryVector;
|
||||
DirectoryVector directories;
|
||||
|
||||
SGPath installedCopyPath;
|
||||
};
|
||||
|
||||
class HTTPDirectory
|
||||
@@ -255,6 +256,54 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
void copyInstalledChildren()
|
||||
{
|
||||
if (_repository->installedCopyPath.isNull()) {
|
||||
return;
|
||||
}
|
||||
|
||||
string_list indexNames = indexChildren();
|
||||
const_string_list_iterator nameIt = indexNames.begin();
|
||||
for (; nameIt != indexNames.end(); ++nameIt) {
|
||||
SGPath p(absolutePath());
|
||||
p.append(*nameIt);
|
||||
if (p.exists()) {
|
||||
continue; // only copy if the file is missing entirely
|
||||
}
|
||||
|
||||
ChildInfoList::iterator c = findIndexChild(*nameIt);
|
||||
if (c->type == ChildInfo::DirectoryType) {
|
||||
continue; // only care about files
|
||||
}
|
||||
|
||||
SGPath cp = _repository->installedCopyPath;
|
||||
cp.append(relativePath());
|
||||
cp.append(*nameIt);
|
||||
if (!cp.exists()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
SG_LOG(SG_TERRASYNC, SG_BULK, "new child, copying existing file" << cp << p);
|
||||
|
||||
SGBinaryFile src(cp);
|
||||
SGBinaryFile dst(p);
|
||||
src.open(SG_IO_IN);
|
||||
dst.open(SG_IO_OUT);
|
||||
|
||||
char* buf = (char*) malloc(cp.sizeInBytes());
|
||||
if (!buf) {
|
||||
continue;
|
||||
}
|
||||
|
||||
src.read(buf, cp.sizeInBytes());
|
||||
dst.write(buf, cp.sizeInBytes());
|
||||
src.close();
|
||||
dst.close();
|
||||
|
||||
free(buf);
|
||||
}
|
||||
}
|
||||
|
||||
void updateChildrenBasedOnHash()
|
||||
{
|
||||
// if we got here for a dir which is still updating or excluded
|
||||
@@ -263,6 +312,8 @@ public:
|
||||
return;
|
||||
}
|
||||
|
||||
copyInstalledChildren();
|
||||
|
||||
string_list indexNames = indexChildren(),
|
||||
toBeUpdated, orphans;
|
||||
simgear::Dir d(absolutePath());
|
||||
@@ -723,6 +774,11 @@ size_t HTTPRepository::bytesDownloaded() const
|
||||
return result;
|
||||
}
|
||||
|
||||
void HTTPRepository::setInstalledCopyPath(const SGPath& copyPath)
|
||||
{
|
||||
_d->installedCopyPath = copyPath;
|
||||
}
|
||||
|
||||
HTTPRepository::ResultCode
|
||||
HTTPRepository::failure() const
|
||||
{
|
||||
|
||||
@@ -71,6 +71,12 @@ public:
|
||||
virtual size_t bytesToDownload() const;
|
||||
|
||||
virtual size_t bytesDownloaded() const;
|
||||
|
||||
/**
|
||||
* optionally provide the location of an installer copy of this
|
||||
* repository. When a file is missing it will be copied from this tree.
|
||||
*/
|
||||
void setInstalledCopyPath(const SGPath& copyPath);
|
||||
private:
|
||||
bool isBare() const;
|
||||
|
||||
|
||||
@@ -274,6 +274,8 @@ public:
|
||||
void setLocalDir(string dir) { _local_dir = stripPath(dir);}
|
||||
string getLocalDir() { return _local_dir;}
|
||||
|
||||
void setInstalledDir(const SGPath& p) { _installRoot = p; }
|
||||
|
||||
void setAllowedErrorCount(int errors)
|
||||
{
|
||||
SGGuard<SGMutex> g(_stateLock);
|
||||
@@ -331,6 +333,7 @@ private:
|
||||
string _local_dir;
|
||||
SGPath _persistentCachePath;
|
||||
string _httpServer;
|
||||
SGPath _installRoot;
|
||||
|
||||
TerrasyncThreadState _state;
|
||||
SGMutex _stateLock;
|
||||
@@ -547,6 +550,12 @@ void SGTerraSync::WorkerThread::updateSyncSlot(SyncSlot &slot)
|
||||
slot.repository->setEntireRepositoryMode();
|
||||
slot.repository->setBaseUrl(_httpServer + "/" + slot.currentItem._dir);
|
||||
|
||||
if (_installRoot.exists()) {
|
||||
SGPath p = _installRoot;
|
||||
p.append(slot.currentItem._dir);
|
||||
slot.repository->setInstalledCopyPath(p);
|
||||
}
|
||||
|
||||
try {
|
||||
slot.repository->update();
|
||||
} catch (sg_exception& e) {
|
||||
@@ -825,6 +834,9 @@ void SGTerraSync::reinit()
|
||||
std::string httpServer(_terraRoot->getStringValue("http-server",""));
|
||||
_workerThread->setHTTPServer(httpServer);
|
||||
_workerThread->setLocalDir(_terraRoot->getStringValue("scenery-dir",""));
|
||||
|
||||
SGPath installPath(_terraRoot->getStringValue("installation-dir"));
|
||||
_workerThread->setInstalledDir(installPath);
|
||||
_workerThread->setAllowedErrorCount(_terraRoot->getIntValue("max-errors",5));
|
||||
_workerThread->setCacheHits(_terraRoot->getIntValue("cache-hit", 0));
|
||||
|
||||
|
||||
Reference in New Issue
Block a user