summaryrefslogtreecommitdiff
path: root/indra/llfilesystem
diff options
context:
space:
mode:
Diffstat (limited to 'indra/llfilesystem')
-rw-r--r--indra/llfilesystem/CMakeLists.txt11
-rw-r--r--indra/llfilesystem/lldir.cpp67
-rw-r--r--indra/llfilesystem/lldir.h2
-rw-r--r--indra/llfilesystem/lldir_linux.cpp18
-rw-r--r--indra/llfilesystem/lldir_linux.h1
-rw-r--r--indra/llfilesystem/lldir_mac.cpp24
-rw-r--r--indra/llfilesystem/lldir_mac.h1
-rw-r--r--indra/llfilesystem/lldir_win32.cpp22
-rw-r--r--indra/llfilesystem/lldir_win32.h1
-rw-r--r--indra/llfilesystem/lldiriterator.cpp21
-rw-r--r--indra/llfilesystem/lldiskcache.cpp137
-rw-r--r--indra/llfilesystem/llfilesystem.cpp108
-rw-r--r--indra/llfilesystem/llfilesystem.h7
-rw-r--r--indra/llfilesystem/lllfsthread.cpp1
-rw-r--r--indra/llfilesystem/tests/lldir_test.cpp37
15 files changed, 149 insertions, 309 deletions
diff --git a/indra/llfilesystem/CMakeLists.txt b/indra/llfilesystem/CMakeLists.txt
index 8d85f739b3..96dc472c4c 100644
--- a/indra/llfilesystem/CMakeLists.txt
+++ b/indra/llfilesystem/CMakeLists.txt
@@ -31,6 +31,12 @@ if (DARWIN)
LIST(APPEND llfilesystem_SOURCE_FILES lldir_utils_objc.h)
LIST(APPEND llfilesystem_SOURCE_FILES lldir_mac.cpp)
LIST(APPEND llfilesystem_HEADER_FILES lldir_mac.h)
+
+ set_source_files_properties(
+ lldir_utils_objc.mm
+ PROPERTIES
+ SKIP_PRECOMPILE_HEADERS TRUE
+ )
endif (DARWIN)
if (LINUX OR CMAKE_SYSTEM_NAME MATCHES FreeBSD)
@@ -55,11 +61,16 @@ list(APPEND llfilesystem_SOURCE_FILES ${llfilesystem_HEADER_FILES})
add_library (llfilesystem ${llfilesystem_SOURCE_FILES})
target_link_libraries(llfilesystem
+ llmath
llcommon
)
target_include_directories( llfilesystem INTERFACE ${CMAKE_CURRENT_SOURCE_DIR})
include(LibraryInstall)
+if (USE_PRECOMPILED_HEADERS)
+ target_precompile_headers(llfilesystem REUSE_FROM llprecompiled)
+endif ()
+
# Add tests
if (LL_TESTS)
include(LLAddBuildTest)
diff --git a/indra/llfilesystem/lldir.cpp b/indra/llfilesystem/lldir.cpp
index a57ac021d9..72f74e1e97 100644
--- a/indra/llfilesystem/lldir.cpp
+++ b/indra/llfilesystem/lldir.cpp
@@ -30,8 +30,6 @@
#include <sys/stat.h>
#include <sys/types.h>
#include <errno.h>
-#else
-#include <direct.h>
#endif
#include "lldir.h"
@@ -43,7 +41,6 @@
#include "lldiriterator.h"
#include "stringize.h"
#include "llstring.h"
-#include <boost/filesystem.hpp>
#include "llprocess.h"
#include <boost/bind.hpp>
#include <algorithm>
@@ -94,34 +91,20 @@ LLDir::~LLDir()
std::vector<std::string> LLDir::getFilesInDir(const std::string &dirname)
{
- //Returns a vector of fullpath filenames.
-
-#ifdef LL_WINDOWS // or BOOST_WINDOWS_API
- boost::filesystem::path p(ll_convert<std::wstring>(dirname));
-#else
- boost::filesystem::path p(dirname);
-#endif
-
+ // Returns a vector of filenames in the directory.
+ fsyspath dir_path(dirname);
std::vector<std::string> v;
-
- boost::system::error_code ec;
- if (exists(p, ec) && !ec.failed())
+ std::error_code ec;
+ if (std::filesystem::is_directory(dir_path, ec))
{
- if (is_directory(p, ec) && !ec.failed())
+ std::filesystem::directory_iterator end_iter;
+ for (std::filesystem::directory_iterator dir_itr(dir_path);
+ dir_itr != end_iter;
+ ++dir_itr)
{
- boost::filesystem::directory_iterator end_iter;
- for (boost::filesystem::directory_iterator dir_itr(p);
- dir_itr != end_iter;
- ++dir_itr)
+ if (std::filesystem::is_regular_file(dir_itr->status()))
{
- if (boost::filesystem::is_regular_file(dir_itr->status()))
- {
-#if LL_WINDOWS
- v.push_back(utf16str_to_utf8str(dir_itr->path().filename().wstring()));
-#else
- v.push_back(dir_itr->path().filename().string());
-#endif
- }
+ v.push_back(dir_itr->path().filename().string());
}
}
}
@@ -194,31 +177,31 @@ U32 LLDir::deleteDirAndContents(const std::string& dir_name)
try
{
-#ifdef LL_WINDOWS // or BOOST_WINDOWS_API
- boost::filesystem::path dir_path(ll_convert<std::wstring>(dir_name));
-#else
- boost::filesystem::path dir_path(dir_name);
-#endif
-
- if (boost::filesystem::exists(dir_path))
+ fsyspath dir_path(dir_name);
+ if (std::filesystem::is_directory(dir_path))
{
- if (!boost::filesystem::is_empty(dir_path))
+ if (!std::filesystem::is_empty(dir_path))
{ // Directory has content
- num_deleted = (U32)boost::filesystem::remove_all(dir_path);
+ num_deleted = (U32)std::filesystem::remove_all(dir_path);
}
else
{ // Directory is empty
- boost::filesystem::remove(dir_path);
+ std::filesystem::remove(dir_path);
}
}
}
- catch (boost::filesystem::filesystem_error &er)
+ catch (std::filesystem::filesystem_error &er)
{
LL_WARNS() << "Failed to delete " << dir_name << " with error " << er.code().message() << LL_ENDL;
}
return num_deleted;
}
+bool LLDir::fileExists(const std::string& filename) const
+{
+ return LLFile::exists(filename);
+}
+
const std::string LLDir::findFile(const std::string &filename,
const std::string& searchPath1,
const std::string& searchPath2,
@@ -1028,7 +1011,7 @@ bool LLDir::setCacheDir(const std::string &path)
{
LLFile::mkdir(path);
std::string tempname = add(path, "temp");
- LLFILE* file = LLFile::fopen(tempname,"wt");
+ LLFILE* file = LLFile::fopen(tempname, LLFILE_MODE("wt"));
if (file)
{
fclose(file);
@@ -1168,15 +1151,15 @@ void dir_exists_or_crash(const std::string &dir_name)
#if LL_WINDOWS
// *FIX: lame - it doesn't do the same thing on windows. not so
// important since we don't deploy simulator to windows boxes.
- LLFile::mkdir(dir_name, 0700);
+ LLFile::mkdir(dir_name);
#else
- struct stat dir_stat;
+ llstat dir_stat;
if(0 != LLFile::stat(dir_name, &dir_stat))
{
S32 stat_rv = errno;
if(ENOENT == stat_rv)
{
- if(0 != LLFile::mkdir(dir_name, 0700)) // octal
+ if(0 != LLFile::mkdir(dir_name))
{
LL_ERRS() << "Unable to create directory: " << dir_name << LL_ENDL;
}
diff --git a/indra/llfilesystem/lldir.h b/indra/llfilesystem/lldir.h
index 3c8e2e2da6..8742b7f937 100644
--- a/indra/llfilesystem/lldir.h
+++ b/indra/llfilesystem/lldir.h
@@ -71,7 +71,7 @@ class LLDir
std::vector<std::string> getFilesInDir(const std::string &dirname);
// pure virtual functions
virtual std::string getCurPath() = 0;
- virtual bool fileExists(const std::string &filename) const = 0;
+ virtual bool fileExists(const std::string &filename) const;
const std::string findFile(const std::string& filename, const std::vector<std::string> filenames) const;
const std::string findFile(const std::string& filename, const std::string& searchPath1 = "", const std::string& searchPath2 = "", const std::string& searchPath3 = "") const;
diff --git a/indra/llfilesystem/lldir_linux.cpp b/indra/llfilesystem/lldir_linux.cpp
index 69cfedebc7..dba479c195 100644
--- a/indra/llfilesystem/lldir_linux.cpp
+++ b/indra/llfilesystem/lldir_linux.cpp
@@ -246,24 +246,6 @@ std::string LLDir_Linux::getCurPath()
return tmp_str;
}
-
-bool LLDir_Linux::fileExists(const std::string &filename) const
-{
- struct stat stat_data;
- // Check the age of the file
- // Now, we see if the files we've gathered are recent...
- int res = stat(filename.c_str(), &stat_data);
- if (!res)
- {
- return true;
- }
- else
- {
- return false;
- }
-}
-
-
/*virtual*/ std::string LLDir_Linux::getLLPluginLauncher()
{
return gDirUtilp->getExecutableDir() + gDirUtilp->getDirDelimiter() +
diff --git a/indra/llfilesystem/lldir_linux.h b/indra/llfilesystem/lldir_linux.h
index f9b0427ccd..ef7206430a 100644
--- a/indra/llfilesystem/lldir_linux.h
+++ b/indra/llfilesystem/lldir_linux.h
@@ -47,7 +47,6 @@ public:
virtual std::string getCurPath();
virtual U32 countFilesInDir(const std::string &dirname, const std::string &mask);
- /*virtual*/ bool fileExists(const std::string &filename) const;
/*virtual*/ std::string getLLPluginLauncher();
/*virtual*/ std::string getLLPluginFilename(std::string base_name);
diff --git a/indra/llfilesystem/lldir_mac.cpp b/indra/llfilesystem/lldir_mac.cpp
index 8b9bdd9853..f6181d7be4 100644
--- a/indra/llfilesystem/lldir_mac.cpp
+++ b/indra/llfilesystem/lldir_mac.cpp
@@ -35,7 +35,7 @@
#include <sys/stat.h>
#include <unistd.h>
#include <glob.h>
-#include <boost/filesystem.hpp>
+#include <filesystem>
#include "lldir_utils_objc.h"
// --------------------------------------------------------------------------------
@@ -45,15 +45,15 @@ static bool CreateDirectory(const std::string &parent,
std::string *fullname)
{
- boost::filesystem::path p(parent);
+ std::filesystem::path p(parent);
p /= child;
if (fullname)
*fullname = std::string(p.string());
- if (! boost::filesystem::create_directory(p))
+ if (! std::filesystem::create_directory(p))
{
- return (boost::filesystem::is_directory(p));
+ return (std::filesystem::is_directory(p));
}
return true;
}
@@ -75,10 +75,8 @@ LLDir_Mac::LLDir_Mac()
// mExecutablePathAndName
mExecutablePathAndName = executablepathstr;
- boost::filesystem::path executablepath(executablepathstr);
+ std::filesystem::path executablepath(executablepathstr);
-# ifndef BOOST_SYSTEM_NO_DEPRECATED
-#endif
mExecutableFilename = executablepath.filename().string();
mExecutableDir = executablepath.parent_path().string();
@@ -140,7 +138,7 @@ LLDir_Mac::LLDir_Mac()
mOSUserAppDir = mOSUserDir;
// mTempDir
- //Aura 120920 boost::filesystem::temp_directory_path() not yet implemented on mac. :(
+ //Aura 120920 std::filesystem::temp_directory_path() not yet implemented on mac. :(
std::string tmpdir = getSystemTempFolder();
if (!tmpdir.empty())
{
@@ -174,17 +172,9 @@ void LLDir_Mac::initAppDirs(const std::string &app_name,
std::string LLDir_Mac::getCurPath()
{
- return boost::filesystem::path( boost::filesystem::current_path() ).string();
+ return std::filesystem::path( std::filesystem::current_path() ).string();
}
-
-
-bool LLDir_Mac::fileExists(const std::string &filename) const
-{
- return boost::filesystem::exists(filename);
-}
-
-
/*virtual*/ std::string LLDir_Mac::getLLPluginLauncher()
{
return gDirUtilp->getAppRODataDir() + gDirUtilp->getDirDelimiter() +
diff --git a/indra/llfilesystem/lldir_mac.h b/indra/llfilesystem/lldir_mac.h
index f812ee810b..54dc2eb237 100644
--- a/indra/llfilesystem/lldir_mac.h
+++ b/indra/llfilesystem/lldir_mac.h
@@ -45,7 +45,6 @@ public:
const std::string& app_read_only_data_dir);
virtual std::string getCurPath();
- virtual bool fileExists(const std::string &filename) const;
/*virtual*/ std::string getLLPluginLauncher();
/*virtual*/ std::string getLLPluginFilename(std::string base_name);
diff --git a/indra/llfilesystem/lldir_win32.cpp b/indra/llfilesystem/lldir_win32.cpp
index 58c080c982..912a2963c6 100644
--- a/indra/llfilesystem/lldir_win32.cpp
+++ b/indra/llfilesystem/lldir_win32.cpp
@@ -52,7 +52,7 @@ namespace
// This is called so early that we can't count on static objects being
// properly constructed yet, so declare a pointer instead of an instance.
- std::ofstream* prelogf = nullptr;
+ llofstream* prelogf = nullptr;
void prelog(const std::string& message)
{
@@ -208,7 +208,7 @@ LLDir_Win32::LLDir_Win32()
{
// successfully created logdir, plunk a log file there
std::string logfilename(add(mOSUserDir, "lldir.log"));
- std::ofstream logfile(logfilename.c_str());
+ llofstream logfile(logfilename.c_str());
if (! logfile.is_open())
{
report(std::cerr);
@@ -373,24 +373,6 @@ std::string LLDir_Win32::getCurPath()
return ll_convert<std::string>(std::wstring(w_str));
}
-
-bool LLDir_Win32::fileExists(const std::string &filename) const
-{
- llstat stat_data;
- // Check the age of the file
- // Now, we see if the files we've gathered are recent...
- int res = LLFile::stat(filename, &stat_data);
- if (!res)
- {
- return true;
- }
- else
- {
- return false;
- }
-}
-
-
/*virtual*/ std::string LLDir_Win32::getLLPluginLauncher()
{
return gDirUtilp->getExecutableDir() + gDirUtilp->getDirDelimiter() +
diff --git a/indra/llfilesystem/lldir_win32.h b/indra/llfilesystem/lldir_win32.h
index 21a3f1213b..c3a41d3e33 100644
--- a/indra/llfilesystem/lldir_win32.h
+++ b/indra/llfilesystem/lldir_win32.h
@@ -44,7 +44,6 @@ public:
/*virtual*/ std::string getCurPath();
/*virtual*/ U32 countFilesInDir(const std::string &dirname, const std::string &mask);
- /*virtual*/ bool fileExists(const std::string &filename) const;
/*virtual*/ std::string getLLPluginLauncher();
/*virtual*/ std::string getLLPluginFilename(std::string base_name);
diff --git a/indra/llfilesystem/lldiriterator.cpp b/indra/llfilesystem/lldiriterator.cpp
index a6eb4adf7f..60b55c7bf3 100644
--- a/indra/llfilesystem/lldiriterator.cpp
+++ b/indra/llfilesystem/lldiriterator.cpp
@@ -24,13 +24,14 @@
* $/LicenseInfo$
*/
+#include "linden_common.h"
+
#include "lldiriterator.h"
-#include "fix_macros.h"
#include "llregex.h"
-#include <boost/filesystem.hpp>
+#include <filesystem>
-namespace fs = boost::filesystem;
+namespace fs = std::filesystem;
static std::string glob_to_regex(const std::string& glob);
@@ -51,11 +52,7 @@ private:
LLDirIterator::Impl::Impl(const std::string &dirname, const std::string &mask)
: mIsValid(false)
{
-#ifdef LL_WINDOWS // or BOOST_WINDOWS_API
- fs::path dir_path(ll_convert<std::wstring>(dirname));
-#else
- fs::path dir_path(dirname);
-#endif
+ fs::path dir_path = fsyspath(dirname);
bool is_dir = false;
@@ -72,11 +69,7 @@ LLDirIterator::Impl::Impl(const std::string &dirname, const std::string &mask)
if (!is_dir)
{
-#if LL_WINDOWS
- LL_WARNS() << "Invalid path: \"" << utf16str_to_utf8str(dir_path.wstring()) << "\"" << LL_ENDL;
-#else
LL_WARNS() << "Invalid path: \"" << dir_path.string() << "\"" << LL_ENDL;
-#endif
return;
}
@@ -134,11 +127,7 @@ bool LLDirIterator::Impl::next(std::string &fname)
while (mIter != end_itr && !found)
{
boost::smatch match;
-#if LL_WINDOWS
- std::string name = utf16str_to_utf8str(mIter->path().filename().wstring());
-#else
std::string name = mIter->path().filename().string();
-#endif
found = ll_regex_match(name, match, mFilterExp);
if (found)
{
diff --git a/indra/llfilesystem/lldiskcache.cpp b/indra/llfilesystem/lldiskcache.cpp
index fafe959ac6..e7b43e15e2 100644
--- a/indra/llfilesystem/lldiskcache.cpp
+++ b/indra/llfilesystem/lldiskcache.cpp
@@ -34,8 +34,8 @@
#include "llapp.h"
#include "llassettype.h"
#include "lldir.h"
-#include <boost/filesystem.hpp>
#include <chrono>
+#include <filesystem>
#include "lldiskcache.h"
@@ -64,10 +64,10 @@ LLDiskCache::LLDiskCache(const std::string& cache_dir,
// WARNING: purge() is called by LLPurgeDiskCacheThread. As such it must
// NOT touch any LLDiskCache data without introducing and locking a mutex!
-// Interaction through the filesystem itself should be safe. Let’s say thread
+// Interaction through the filesystem itself should be safe. Let's say thread
// A is accessing the cache file for reading/writing and thread B is trimming
-// the cache. Let’s also assume using llifstream to open a file and
-// boost::filesystem::remove are not atomic (which will be pretty much the
+// the cache. Let's also assume using llifstream to open a file and
+// std::filesystem::remove are not atomic (which will be pretty much the
// case).
// Now, A is trying to open the file using llifstream ctor. It does some
@@ -83,7 +83,7 @@ LLDiskCache::LLDiskCache(const std::string& cache_dir,
// garbage.)
// Other situation: B is trimming the cache and A wants to read a file that is
-// about to get deleted. boost::filesystem::remove does whatever it is doing
+// about to get deleted. std::filesystem::remove does whatever it is doing
// before actually deleting the file. If A opens the file before the file is
// actually gone, the OS call from B to delete the file will fail since the OS
// will prevent this. B continues with the next file. If the file is already
@@ -98,46 +98,34 @@ void LLDiskCache::purge()
LL_INFOS() << "Total dir size before purge is " << dirFileSize(sCacheDir) << LL_ENDL;
}
- boost::system::error_code ec;
+ std::error_code ec;
auto start_time = std::chrono::high_resolution_clock::now();
- typedef std::pair<std::time_t, std::pair<uintmax_t, std::string>> file_info_t;
+ typedef std::pair<std::filesystem::file_time_type, std::pair<uintmax_t, std::string>> file_info_t;
std::vector<file_info_t> file_info;
-#if LL_WINDOWS
- std::wstring cache_path(ll_convert<std::wstring>(sCacheDir));
-#else
- std::string cache_path(sCacheDir);
-#endif
- if (boost::filesystem::is_directory(cache_path, ec) && !ec.failed())
+ std::filesystem::path cache_path = fsyspath(sCacheDir);
+ if (std::filesystem::is_directory(cache_path, ec) && !ec)
{
- boost::filesystem::directory_iterator iter(cache_path, ec);
- while (iter != boost::filesystem::directory_iterator() && !ec.failed())
+ std::filesystem::directory_iterator iter(cache_path, ec);
+ while (iter != std::filesystem::directory_iterator() && !ec)
{
if(!LLApp::isRunning())
{
return;
}
- if (boost::filesystem::is_regular_file(*iter, ec) && !ec.failed())
+ if (std::filesystem::is_regular_file(*iter, ec) && !ec)
{
-#if LL_WINDOWS
- if (utf16str_to_utf8str((*iter).path().wstring()).find(CACHE_FILENAME_PREFIX) != std::string::npos)
-#else
if ((*iter).path().string().find(CACHE_FILENAME_PREFIX) != std::string::npos)
-#endif
{
- uintmax_t file_size = boost::filesystem::file_size(*iter, ec);
- if (ec.failed())
+ uintmax_t file_size = std::filesystem::file_size(*iter, ec);
+ if (ec)
{
continue;
}
-#if LL_WINDOWS
- const std::string file_path = utf16str_to_utf8str((*iter).path().wstring());
-#else
const std::string file_path = (*iter).path().string();
-#endif
- const std::time_t file_time = boost::filesystem::last_write_time(*iter, ec);
- if (ec.failed())
+ const std::filesystem::file_time_type file_time = std::filesystem::last_write_time(*iter, ec);
+ if (ec)
{
continue;
}
@@ -177,16 +165,10 @@ void LLDiskCache::purge()
}
if (should_remove)
{
-#if LL_WINDOWS
- boost::filesystem::remove(utf8str_to_utf16str(entry.second.second), ec);
-#else
- boost::filesystem::remove(entry.second.second, ec);
-#endif
- if (ec.failed())
+ std::filesystem::remove(entry.second.second, ec);
+ if (ec)
{
-#if !LL_WINDOWS
LL_WARNS() << "Failed to delete cache file " << entry.second.second << ": " << ec.message() << LL_ENDL;
-#endif
}
}
}
@@ -212,7 +194,7 @@ void LLDiskCache::purge()
std::ostringstream line;
line << action << " ";
- line << entry.first << " ";
+ line << S64(entry.first.time_since_epoch().count()) << " ";
line << entry.second.first << " ";
line << entry.second.second;
line << " (" << file_size_total << "/" << mMaxSizeBytes << ")";
@@ -226,7 +208,9 @@ void LLDiskCache::purge()
const std::string LLDiskCache::metaDataToFilepath(const LLUUID& id, LLAssetType::EType at)
{
- return llformat("%s%s%s_%s_0.asset", sCacheDir.c_str(), gDirUtilp->getDirDelimiter().c_str(), CACHE_FILENAME_PREFIX.c_str(), id.asString().c_str());
+ char uuid_str[UUID_STR_LENGTH]{};
+ id.to_chars(uuid_str);
+ return llformat("%s%s%s_%s_0.asset", sCacheDir.c_str(), gDirUtilp->getDirDelimiter().c_str(), CACHE_FILENAME_PREFIX.c_str(), uuid_str);
}
const std::string LLDiskCache::getCacheInfo()
@@ -252,31 +236,21 @@ void LLDiskCache::clearCache()
* the component files but it's called infrequently so it's
* likely just fine
*/
- boost::system::error_code ec;
-#if LL_WINDOWS
- std::wstring cache_path(ll_convert<std::wstring>(sCacheDir));
-#else
- std::string cache_path(sCacheDir);
-#endif
- if (boost::filesystem::is_directory(cache_path, ec) && !ec.failed())
+ std::error_code ec;
+ std::filesystem::path cache_path = fsyspath(sCacheDir);
+ if (std::filesystem::is_directory(cache_path, ec) && !ec)
{
- boost::filesystem::directory_iterator iter(cache_path, ec);
- while (iter != boost::filesystem::directory_iterator() && !ec.failed())
+ std::filesystem::directory_iterator iter(cache_path, ec);
+ while (iter != std::filesystem::directory_iterator() && !ec)
{
- if (boost::filesystem::is_regular_file(*iter, ec) && !ec.failed())
+ if (std::filesystem::is_regular_file(*iter, ec) && !ec)
{
-#if LL_WINDOWS
- if (utf16str_to_utf8str((*iter).path().wstring()).find(CACHE_FILENAME_PREFIX) != std::string::npos)
-#else
if ((*iter).path().string().find(CACHE_FILENAME_PREFIX) != std::string::npos)
-#endif
{
- boost::filesystem::remove(*iter, ec);
- if (ec.failed())
+ std::filesystem::remove(*iter, ec);
+ if (ec)
{
-#if !LL_WINDOWS
LL_WARNS() << "Failed to delete cache file " << *iter << ": " << ec.message() << LL_ENDL;
-#endif
}
}
}
@@ -291,33 +265,22 @@ void LLDiskCache::removeOldVFSFiles()
static const char CACHE_FORMAT[] = "inv.llsd";
static const char DB_FORMAT[] = "db2.x";
- boost::system::error_code ec;
-#if LL_WINDOWS
- std::wstring cache_path(ll_convert<std::wstring>(gDirUtilp->getExpandedFilename(LL_PATH_CACHE, "")));
-#else
- std::string cache_path(gDirUtilp->getExpandedFilename(LL_PATH_CACHE, ""));
-#endif
- if (boost::filesystem::is_directory(cache_path, ec) && !ec.failed())
+ std::error_code ec;
+ std::filesystem::path cache_path = fsyspath(gDirUtilp->getExpandedFilename(LL_PATH_CACHE, ""));
+ if (std::filesystem::is_directory(cache_path, ec) && !ec)
{
- boost::filesystem::directory_iterator iter(cache_path, ec);
- while (iter != boost::filesystem::directory_iterator() && !ec.failed())
+ std::filesystem::directory_iterator iter(cache_path, ec);
+ while (iter != std::filesystem::directory_iterator() && !ec)
{
- if (boost::filesystem::is_regular_file(*iter, ec) && !ec.failed())
+ if (std::filesystem::is_regular_file(*iter, ec) && !ec)
{
-#if LL_WINDOWS
- if ((utf16str_to_utf8str((*iter).path().wstring()).find(CACHE_FORMAT) != std::string::npos) ||
- (utf16str_to_utf8str((*iter).path().wstring()).find(DB_FORMAT) != std::string::npos))
-#else
if (((*iter).path().string().find(CACHE_FORMAT) != std::string::npos) ||
((*iter).path().string().find(DB_FORMAT) != std::string::npos))
-#endif
{
- boost::filesystem::remove(*iter, ec);
- if (ec.failed())
+ std::filesystem::remove(*iter, ec);
+ if (ec)
{
-#if !LL_WINDOWS
LL_WARNS() << "Failed to delete cache file " << *iter << ": " << ec.message() << LL_ENDL;
-#endif
}
}
}
@@ -339,27 +302,19 @@ uintmax_t LLDiskCache::dirFileSize(const std::string& dir)
* so if performance is ever an issue, optimizing this or removing it altogether,
* is an easy win.
*/
- boost::system::error_code ec;
-#if LL_WINDOWS
- std::wstring dir_path(ll_convert<std::wstring>(dir));
-#else
- std::string dir_path(dir);
-#endif
- if (boost::filesystem::is_directory(dir_path, ec) && !ec.failed())
+ std::error_code ec;
+ std::filesystem::path dir_path = fsyspath(dir);
+ if (std::filesystem::is_directory(dir_path, ec) && !ec)
{
- boost::filesystem::directory_iterator iter(dir_path, ec);
- while (iter != boost::filesystem::directory_iterator() && !ec.failed())
+ std::filesystem::directory_iterator iter(dir_path, ec);
+ while (iter != std::filesystem::directory_iterator() && !ec)
{
- if (boost::filesystem::is_regular_file(*iter, ec) && !ec.failed())
+ if (std::filesystem::is_regular_file(*iter, ec) && !ec)
{
-#if LL_WINDOWS
- if (utf16str_to_utf8str((*iter).path().wstring()).find(CACHE_FILENAME_PREFIX) != std::string::npos)
-#else
if ((*iter).path().string().find(CACHE_FILENAME_PREFIX) != std::string::npos)
-#endif
{
- uintmax_t file_size = boost::filesystem::file_size(*iter, ec);
- if (!ec.failed())
+ uintmax_t file_size = std::filesystem::file_size(*iter, ec);
+ if (!ec)
{
total_file_size += file_size;
}
diff --git a/indra/llfilesystem/llfilesystem.cpp b/indra/llfilesystem/llfilesystem.cpp
index cd0ce45049..388cbc280f 100644
--- a/indra/llfilesystem/llfilesystem.cpp
+++ b/indra/llfilesystem/llfilesystem.cpp
@@ -34,8 +34,6 @@
#include "llfasttimer.h"
#include "lldiskcache.h"
-#include "boost/filesystem.hpp"
-
constexpr S32 LLFileSystem::READ = 0x00000001;
constexpr S32 LLFileSystem::WRITE = 0x00000002;
constexpr S32 LLFileSystem::READ_WRITE = 0x00000003; // LLFileSystem::READ & LLFileSystem::WRITE
@@ -51,22 +49,21 @@ LLFileSystem::LLFileSystem(const LLUUID& file_id, const LLAssetType::EType file_
mBytesRead = 0;
mMode = mode;
+ // build the filepath
+ mPath = fsyspath(LLDiskCache::metaDataToFilepath(mFileID, mFileType));
+
// This block of code was originally called in the read() method but after comments here:
// https://bitbucket.org/lindenlab/viewer/commits/e28c1b46e9944f0215a13cab8ee7dded88d7fc90#comment-10537114
// we decided to follow Henri's suggestion and move the code to update the last access time here.
if (mode == LLFileSystem::READ)
{
- // build the filename (TODO: we do this in a few places - perhaps we should factor into a single function)
- const std::string filename = LLDiskCache::metaDataToFilepath(mFileID, mFileType);
-
// update the last access time for the file if it exists - this is required
// even though we are reading and not writing because this is the
// way the cache works - it relies on a valid "last accessed time" for
// each file so it knows how to remove the oldest, unused files
- bool exists = gDirUtilp->fileExists(filename);
- if (exists)
+ if (LLFile::exists(mPath))
{
- updateFileAccessTime(filename);
+ updateFileAccessTime();
}
}
}
@@ -75,26 +72,19 @@ LLFileSystem::LLFileSystem(const LLUUID& file_id, const LLAssetType::EType file_
bool LLFileSystem::getExists(const LLUUID& file_id, const LLAssetType::EType file_type)
{
LL_PROFILE_ZONE_SCOPED;
-#if LL_WINDOWS
- const auto filename = ll_convert<std::wstring>(LLDiskCache::metaDataToFilepath(file_id, file_type));
-#else
const std::string filename = LLDiskCache::metaDataToFilepath(file_id, file_type);
-#endif
- boost::system::error_code ec;
- if (boost::filesystem::exists(filename, ec) && boost::filesystem::is_regular_file(filename, ec))
- {
- return boost::filesystem::file_size(filename, ec) > 0;
- }
- return false;
+ // not only test for existence but for the file to be not empty
+ S64 size = LLFile::size(filename);
+ return size > 0;
}
// static
-bool LLFileSystem::removeFile(const LLUUID& file_id, const LLAssetType::EType file_type, int suppress_error /*= 0*/)
+bool LLFileSystem::removeFile(const LLUUID& file_id, const LLAssetType::EType file_type, int suppress_warning /*= 0*/)
{
const std::string filename = LLDiskCache::metaDataToFilepath(file_id, file_type);
- LLFile::remove(filename.c_str(), suppress_error);
+ LLFile::remove(filename.c_str(), suppress_warning);
return true;
}
@@ -118,30 +108,11 @@ bool LLFileSystem::renameFile(const LLUUID& old_file_id, const LLAssetType::ETyp
return true;
}
-// static
-S32 LLFileSystem::getFileSize(const LLUUID& file_id, const LLAssetType::EType file_type)
-{
-#if LL_WINDOWS
- const auto filename = ll_convert<std::wstring>(LLDiskCache::metaDataToFilepath(file_id, file_type));
-#else
- const std::string filename = LLDiskCache::metaDataToFilepath(file_id, file_type);
-#endif
-
- boost::system::error_code ec;
- if (boost::filesystem::exists(filename, ec) && boost::filesystem::is_regular_file(filename, ec))
- {
- return static_cast<S32>(boost::filesystem::file_size(filename, ec));
- }
- return 0;
-}
-
bool LLFileSystem::read(U8* buffer, S32 bytes)
{
bool success = false;
- const std::string filename = LLDiskCache::metaDataToFilepath(mFileID, mFileType);
-
- llifstream file(filename, std::ios::binary);
+ llifstream file(mPath, std::ios::binary);
if (file.is_open())
{
file.seekg(mPosition, std::ios::beg);
@@ -181,13 +152,11 @@ bool LLFileSystem::eof() const
bool LLFileSystem::write(const U8* buffer, S32 bytes)
{
- const std::string filename = LLDiskCache::metaDataToFilepath(mFileID, mFileType);
-
bool success = false;
if (mMode == APPEND)
{
- llofstream ofs(filename, std::ios::app | std::ios::binary);
+ llofstream ofs(mPath, std::ios::app | std::ios::binary);
if (ofs)
{
ofs.write((const char*)buffer, bytes);
@@ -200,7 +169,7 @@ bool LLFileSystem::write(const U8* buffer, S32 bytes)
else if (mMode == READ_WRITE)
{
// Don't truncate if file already exists
- llofstream ofs(filename, std::ios::in | std::ios::binary);
+ llofstream ofs(mPath, std::ios::in | std::ios::binary);
if (ofs)
{
ofs.seekp(mPosition, std::ios::beg);
@@ -211,7 +180,7 @@ bool LLFileSystem::write(const U8* buffer, S32 bytes)
else
{
// File doesn't exist - open in write mode
- ofs.open(filename, std::ios::binary);
+ ofs.open(mPath, std::ios::binary);
if (ofs.is_open())
{
ofs.write((const char*)buffer, bytes);
@@ -222,7 +191,7 @@ bool LLFileSystem::write(const U8* buffer, S32 bytes)
}
else
{
- llofstream ofs(filename, std::ios::binary);
+ llofstream ofs(mPath, std::ios::binary);
if (ofs)
{
ofs.write((const char*)buffer, bytes);
@@ -273,7 +242,7 @@ S32 LLFileSystem::tell() const
S32 LLFileSystem::getSize() const
{
- return LLFileSystem::getFileSize(mFileID, mFileType);
+ return narrow(LLFile::size(mPath));
}
S32 LLFileSystem::getMaxSize() const
@@ -288,17 +257,18 @@ bool LLFileSystem::rename(const LLUUID& new_id, const LLAssetType::EType new_typ
mFileID = new_id;
mFileType = new_type;
+ mPath = fsyspath(LLDiskCache::metaDataToFilepath(mFileID, mFileType));
return true;
}
bool LLFileSystem::remove() const
{
- LLFileSystem::removeFile(mFileID, mFileType);
+ LLFile::remove(mPath);
return true;
}
-void LLFileSystem::updateFileAccessTime(const std::string& file_path)
+void LLFileSystem::updateFileAccessTime()
{
/**
* Threshold in time_t units that is used to decide if the last access time
@@ -309,52 +279,32 @@ void LLFileSystem::updateFileAccessTime(const std::string& file_path)
*
* Let's start with 1 hour in time_t units and see how that unfolds
*/
- constexpr std::time_t time_threshold = 1 * 60 * 60;
+ constexpr std::chrono::hours time_threshold(1);
// current time
- const std::time_t cur_time = std::time(nullptr);
+ const std::filesystem::file_time_type cur_time = std::chrono::file_clock::now();
- boost::system::error_code ec;
-#if LL_WINDOWS
- // file last write time
- const std::time_t last_write_time = boost::filesystem::last_write_time(ll_convert<std::wstring>(file_path), ec);
- if (ec.failed())
- {
- LL_WARNS() << "Failed to read last write time for cache file " << file_path << ": " << ec.message() << LL_ENDL;
- return;
- }
-
- // delta between cur time and last time the file was written
- const std::time_t delta_time = cur_time - last_write_time;
-
- // we only write the new value if the time in time_threshold has elapsed
- // before the last one
- if (delta_time > time_threshold)
- {
- boost::filesystem::last_write_time(ll_convert<std::wstring>(file_path), cur_time, ec);
- }
-#else
+ std::error_code ec;
// file last write time
- const std::time_t last_write_time = boost::filesystem::last_write_time(file_path, ec);
- if (ec.failed())
+ const std::filesystem::file_time_type last_write_time = std::filesystem::last_write_time(mPath, ec);
+ if (ec)
{
- LL_WARNS() << "Failed to read last write time for cache file " << file_path << ": " << ec.message() << LL_ENDL;
+ LL_WARNS() << "Failed to read last write time for cache file " << mPath << ": " << ec.message() << LL_ENDL;
return;
}
// delta between cur time and last time the file was written
- const std::time_t delta_time = cur_time - last_write_time;
+ const auto delta_time = cur_time - last_write_time;
// we only write the new value if the time in time_threshold has elapsed
// before the last one
if (delta_time > time_threshold)
{
- boost::filesystem::last_write_time(file_path, cur_time, ec);
+ std::filesystem::last_write_time(mPath, cur_time, ec);
}
-#endif
- if (ec.failed())
+ if (ec)
{
- LL_WARNS() << "Failed to update last write time for cache file " << file_path << ": " << ec.message() << LL_ENDL;
+ LL_WARNS() << "Failed to update last write time for cache file " << mPath << ": " << ec.message() << LL_ENDL;
}
}
diff --git a/indra/llfilesystem/llfilesystem.h b/indra/llfilesystem/llfilesystem.h
index 10649b6920..bc8b9216bd 100644
--- a/indra/llfilesystem/llfilesystem.h
+++ b/indra/llfilesystem/llfilesystem.h
@@ -33,6 +33,7 @@
#include "lluuid.h"
#include "llassettype.h"
#include "lldiskcache.h"
+#include <filesystem>
class LLFileSystem
{
@@ -58,13 +59,12 @@ class LLFileSystem
* file in the cache is read (not written) so that the last time the file was
* accessed is up to date (This is used in the mechanism for purging the cache)
*/
- void updateFileAccessTime(const std::string& file_path);
+ void updateFileAccessTime();
static bool getExists(const LLUUID& file_id, const LLAssetType::EType file_type);
- static bool removeFile(const LLUUID& file_id, const LLAssetType::EType file_type, int suppress_error = 0);
+ static bool removeFile(const LLUUID& file_id, const LLAssetType::EType file_type, int suppress_warning = 0);
static bool renameFile(const LLUUID& old_file_id, const LLAssetType::EType old_file_type,
const LLUUID& new_file_id, const LLAssetType::EType new_file_type);
- static S32 getFileSize(const LLUUID& file_id, const LLAssetType::EType file_type);
public:
static const S32 READ;
@@ -73,6 +73,7 @@ class LLFileSystem
static const S32 APPEND;
protected:
+ std::filesystem::path mPath;
LLAssetType::EType mFileType;
LLUUID mFileID;
S32 mPosition;
diff --git a/indra/llfilesystem/lllfsthread.cpp b/indra/llfilesystem/lllfsthread.cpp
index 6a882f64a8..69f7085290 100644
--- a/indra/llfilesystem/lllfsthread.cpp
+++ b/indra/llfilesystem/lllfsthread.cpp
@@ -51,6 +51,7 @@ S32 LLLFSThread::updateClass(U32 ms_elapsed)
//static
void LLLFSThread::cleanupClass()
{
+ LL_PROFILE_ZONE_SCOPED;
llassert(sLocal != NULL);
sLocal->setQuitting();
while (sLocal->getPending())
diff --git a/indra/llfilesystem/tests/lldir_test.cpp b/indra/llfilesystem/tests/lldir_test.cpp
index 13db6fad80..412feb147b 100644
--- a/indra/llfilesystem/tests/lldir_test.cpp
+++ b/indra/llfilesystem/tests/lldir_test.cpp
@@ -27,12 +27,14 @@
#include "linden_common.h"
+#include <filesystem>
#include "llstring.h"
#include "tests/StringVec.h"
#include "../lldir.h"
#include "../lldiriterator.h"
#include "../test/lltut.h"
+#include "../test/namedtempfile.h"
#include "stringize.h"
// For some tests, use a dummy LLDir that uses memory data instead of touching
@@ -403,7 +405,7 @@ namespace tut
std::string makeTestFile( const std::string& dir, const std::string& file )
{
std::string path = dir + file;
- LLFILE* handle = LLFile::fopen( path, "w" );
+ LLFILE* handle = LLFile::fopen(path, LLFILE_MODE("w"));
ensure("failed to open test file '"+path+"'", handle != NULL );
// Harbison & Steele, 4th ed., p. 366: "If an error occurs, fputs
// returns EOF; otherwise, it returns some other, nonnegative value."
@@ -412,23 +414,19 @@ namespace tut
return path;
}
- std::string makeTestDir( const std::string& dirbase )
+ std::string makeTestDir( )
{
- int counter;
- std::string uniqueDir;
- bool foundUnused;
- std::string delim = gDirUtilp->getDirDelimiter();
+ auto p = NamedTempFile::temp_path();
+ std::filesystem::create_directories(p.native());
- for (counter=0, foundUnused=false; !foundUnused; counter++ )
- {
- char counterStr[3];
- snprintf(counterStr, sizeof(counterStr), "%02d", counter);
- uniqueDir = dirbase + counterStr;
- foundUnused = ! ( LLFile::isdir(uniqueDir) || LLFile::isfile(uniqueDir) );
- }
- ensure("test directory '" + uniqueDir + "' creation failed", !LLFile::mkdir(uniqueDir));
+ std::string ret = p.string();
- return uniqueDir + delim; // HACK - apparently, the trailing delimiter is needed...
+ // There's an implicit assumtion all over this code that the returned path ends with "/" (or "\")
+
+ if(ret.size() >= 1 && ret[ ret.size()-1 ] != std::filesystem::path::preferred_separator )
+ ret += std::filesystem::path::preferred_separator;
+
+ return ret;
}
static const char* DirScanFilename[5] = { "file1.abc", "file2.abc", "file1.xyz", "file2.xyz", "file1.mno" };
@@ -484,8 +482,9 @@ namespace tut
// Create the same 5 file names of the two directories
- std::string dir1 = makeTestDir(dirTemp + "LLDirIterator");
- std::string dir2 = makeTestDir(dirTemp + "LLDirIterator");
+ std::string dir1 = makeTestDir();
+ std::string dir2 = makeTestDir();
+
std::string dir1files[5];
std::string dir2files[5];
for (int i=0; i<5; i++)
@@ -558,8 +557,8 @@ namespace tut
LLFile::remove(dir1files[i]);
LLFile::remove(dir2files[i]);
}
- LLFile::rmdir(dir1);
- LLFile::rmdir(dir2);
+ LLFile::remove(dir1);
+ LLFile::remove(dir2);
}
template<> template<>