add support for removing individual files from VFS and a mechanism for automatically doing so (add filename.extension.DELETED to the same directory/archive), as discussed in meeting.
refactor: split up Invalidate into RemoveFile+RepopulateDirectory GameSetup: fix: ensure the first mod always overrides game files, irrespective of timestamp. This was SVN commit r10610.
This commit is contained in:
parent
d82b85b8f3
commit
301854702c
@ -224,15 +224,25 @@ public:
|
||||
return INFO::OK;
|
||||
}
|
||||
|
||||
virtual Status Invalidate(const VfsPath& pathname)
|
||||
virtual Status RemoveFile(const VfsPath& pathname)
|
||||
{
|
||||
ScopedLock s;
|
||||
m_fileCache.Remove(pathname);
|
||||
|
||||
VfsDirectory* directory; VfsFile* file;
|
||||
RETURN_STATUS_IF_ERR(vfs_Lookup(pathname, &m_rootDirectory, directory, &file));
|
||||
directory->RemoveFile(file->Name());
|
||||
|
||||
return INFO::OK;
|
||||
}
|
||||
|
||||
virtual Status RepopulateDirectory(const VfsPath& path)
|
||||
{
|
||||
ScopedLock s;
|
||||
|
||||
VfsDirectory* directory;
|
||||
RETURN_STATUS_IF_ERR(vfs_Lookup(pathname, &m_rootDirectory, directory, 0));
|
||||
const OsPath name = pathname.Filename();
|
||||
directory->Invalidate(name);
|
||||
RETURN_STATUS_IF_ERR(vfs_Lookup(path, &m_rootDirectory, directory, 0));
|
||||
directory->RequestRepopulate();
|
||||
|
||||
return INFO::OK;
|
||||
}
|
||||
|
@ -172,12 +172,19 @@ struct IVFS
|
||||
* directories below a mount point with a matching real path.
|
||||
**/
|
||||
virtual Status GetVirtualPath(const OsPath& realPathname, VfsPath& pathname) = 0;
|
||||
|
||||
|
||||
/**
|
||||
* indicate that a file has changed; remove its data from the cache and
|
||||
* arrange for its directory to be updated.
|
||||
* remove file from the virtual directory listing and evict its
|
||||
* data from the cache.
|
||||
**/
|
||||
virtual Status Invalidate(const VfsPath& pathname) = 0;
|
||||
virtual Status RemoveFile(const VfsPath& pathname) = 0;
|
||||
|
||||
/**
|
||||
* request the directory be re-populated when it is next accessed.
|
||||
* useful for synchronizing with the underlying filesystem after
|
||||
* files have been created or their metadata changed.
|
||||
**/
|
||||
virtual Status RepopulateDirectory(const VfsPath& path) = 0;
|
||||
|
||||
/**
|
||||
* empty the contents of the filesystem.
|
||||
|
@ -69,7 +69,14 @@ public:
|
||||
private:
|
||||
void AddFile(const FileInfo& fileInfo) const
|
||||
{
|
||||
const VfsFile file(fileInfo.Name(), (size_t)fileInfo.Size(), fileInfo.MTime(), m_realDirectory->Priority(), m_realDirectory);
|
||||
const VfsPath name = fileInfo.Name();
|
||||
if(name.Extension() == L".DELETED")
|
||||
{
|
||||
m_directory->RemoveFile(name.Basename());
|
||||
return;
|
||||
}
|
||||
|
||||
const VfsFile file(name, (size_t)fileInfo.Size(), fileInfo.MTime(), m_realDirectory->Priority(), m_realDirectory);
|
||||
const VfsFile* pfile = m_directory->AddFile(file);
|
||||
|
||||
#if ENABLE_ARCHIVE_STATS
|
||||
@ -94,7 +101,15 @@ private:
|
||||
const size_t flags = VFS_LOOKUP_ADD|VFS_LOOKUP_SKIP_POPULATE;
|
||||
VfsDirectory* directory;
|
||||
WARN_IF_ERR(vfs_Lookup(pathname, this_->m_directory, directory, 0, flags));
|
||||
const VfsFile file(fileInfo.Name(), (size_t)fileInfo.Size(), fileInfo.MTime(), this_->m_realDirectory->Priority(), archiveFile);
|
||||
|
||||
const VfsPath name = fileInfo.Name();
|
||||
if(name.Extension() == L".DELETED")
|
||||
{
|
||||
directory->RemoveFile(name.Basename());
|
||||
return;
|
||||
}
|
||||
|
||||
const VfsFile file(name, (size_t)fileInfo.Size(), fileInfo.MTime(), this_->m_realDirectory->Priority(), archiveFile);
|
||||
directory->AddFile(file);
|
||||
#if ENABLE_ARCHIVE_STATS
|
||||
s_numArchivedFiles++;
|
||||
|
@ -106,6 +106,12 @@ VfsDirectory* VfsDirectory::AddSubdirectory(const VfsPath& name)
|
||||
}
|
||||
|
||||
|
||||
void VfsDirectory::RemoveFile(const VfsPath& name)
|
||||
{
|
||||
m_files.erase(name.string());
|
||||
}
|
||||
|
||||
|
||||
VfsFile* VfsDirectory::GetFile(const VfsPath& name)
|
||||
{
|
||||
VfsFiles::iterator it = m_files.find(name.string());
|
||||
@ -138,9 +144,8 @@ bool VfsDirectory::ShouldPopulate()
|
||||
}
|
||||
|
||||
|
||||
void VfsDirectory::Invalidate(const VfsPath& name)
|
||||
void VfsDirectory::RequestRepopulate()
|
||||
{
|
||||
m_files.erase(name.string());
|
||||
m_shouldPopulate = 1;
|
||||
}
|
||||
|
||||
|
@ -93,6 +93,12 @@ public:
|
||||
**/
|
||||
VfsDirectory* AddSubdirectory(const VfsPath& name);
|
||||
|
||||
/**
|
||||
* remove the given file from the virtual directory (no effect on
|
||||
* the physical file). no effect if the file does not exist.
|
||||
**/
|
||||
void RemoveFile(const VfsPath& name);
|
||||
|
||||
/**
|
||||
* @return file with the given name.
|
||||
* (note: non-const to allow changes to the file)
|
||||
@ -135,10 +141,9 @@ public:
|
||||
bool ShouldPopulate();
|
||||
|
||||
/**
|
||||
* indicate that a file has changed; ensure its new version supersedes
|
||||
* the old by removing it and marking the directory for re-population.
|
||||
* ensure the next ShouldPopulate returns true.
|
||||
**/
|
||||
void Invalidate(const VfsPath& name);
|
||||
void RequestRepopulate();
|
||||
|
||||
/**
|
||||
* empty file and subdirectory lists (e.g. when rebuilding VFS).
|
||||
|
@ -78,7 +78,8 @@ Status ReloadChangedFiles()
|
||||
{
|
||||
VfsPath pathname;
|
||||
RETURN_STATUS_IF_ERR(g_VFS->GetVirtualPath(notifications[i].Pathname(), pathname));
|
||||
RETURN_STATUS_IF_ERR(g_VFS->Invalidate(pathname));
|
||||
RETURN_STATUS_IF_ERR(g_VFS->RemoveFile(pathname));
|
||||
RETURN_STATUS_IF_ERR(g_VFS->RepopulateDirectory(pathname.Parent()));
|
||||
|
||||
// Tell each hotloadable system about this file change:
|
||||
|
||||
|
@ -459,7 +459,7 @@ static void InitVfs(const CmdLineArgs& args)
|
||||
OsPath modLoosePath = paths.RData()/"mods";
|
||||
for (size_t i = 0; i < mods.size(); ++i)
|
||||
{
|
||||
size_t priority = i;
|
||||
size_t priority = i+1; // mods are higher priority than regular mountings, which default to priority 0
|
||||
size_t flags = VFS_MOUNT_WATCH|VFS_MOUNT_ARCHIVABLE|VFS_MOUNT_MUST_EXIST;
|
||||
OsPath modName(mods[i]);
|
||||
g_VFS->Mount(L"", modLoosePath / modName/"", flags, priority);
|
||||
|
@ -133,7 +133,8 @@ public:
|
||||
TS_ASSERT_OK(CreateDirectories(DataDir()/"mods"/"_test.sim"/"simulation"/"components"/"hotload"/"", 0700));
|
||||
|
||||
copyFile(L"simulation/components/test-hotload1.js", L"simulation/components/hotload/hotload.js");
|
||||
TS_ASSERT_OK(g_VFS->Invalidate(L"simulation/components/hotload/hotload.js"));
|
||||
TS_ASSERT_OK(g_VFS->RemoveFile(L"simulation/components/hotload/hotload.js"));
|
||||
TS_ASSERT_OK(g_VFS->RepopulateDirectory(L"simulation/components/hotload/"));
|
||||
TS_ASSERT(sim.LoadScripts(L"simulation/components/hotload/"));
|
||||
|
||||
sim.ResetState(true, true);
|
||||
@ -143,7 +144,8 @@ public:
|
||||
TS_ASSERT_EQUALS(static_cast<ICmpTest1*> (sim.QueryInterface(ent, IID_Test1))->GetX(), 100);
|
||||
|
||||
copyFile(L"simulation/components/test-hotload2.js", L"simulation/components/hotload/hotload.js");
|
||||
TS_ASSERT_OK(g_VFS->Invalidate(L"simulation/components/hotload/hotload.js"));
|
||||
TS_ASSERT_OK(g_VFS->RemoveFile(L"simulation/components/hotload/hotload.js"));
|
||||
TS_ASSERT_OK(g_VFS->RepopulateDirectory(L"simulation/components/hotload/"));
|
||||
|
||||
TS_ASSERT_OK(sim.ReloadChangedFile(L"art/irrelevant.xml"));
|
||||
TS_ASSERT_OK(sim.ReloadChangedFile(L"simulation/components/irrelevant.js"));
|
||||
@ -156,7 +158,8 @@ public:
|
||||
TS_ASSERT_EQUALS(static_cast<ICmpTest1*> (sim.QueryInterface(ent, IID_Test1))->GetX(), 1000);
|
||||
|
||||
TS_ASSERT_OK(DeleteDirectory(DataDir()/"mods"/"_test.sim"/"simulation"/"components"/"hotload"/""));
|
||||
TS_ASSERT_OK(g_VFS->Invalidate(L"simulation/components/hotload/hotload.js"));
|
||||
TS_ASSERT_OK(g_VFS->RemoveFile(L"simulation/components/hotload/hotload.js"));
|
||||
TS_ASSERT_OK(g_VFS->RepopulateDirectory(L"simulation/components/hotload/"));
|
||||
|
||||
TS_ASSERT_OK(sim.ReloadChangedFile(L"simulation/components/hotload/hotload.js"));
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user