aboutsummaryrefslogtreecommitdiff
path: root/dep/efsw
diff options
context:
space:
mode:
authordaMaex <damaex@live.de>2019-11-05 18:38:30 +0100
committerShauren <shauren.trinity@gmail.com>2021-12-19 00:01:13 +0100
commit97d48751b0192533f2d7b325d1b9a5dabf99ae73 (patch)
treea77047339244bf29a80a86f9f899496d86463893 /dep/efsw
parentdbf347bdd02d2fe897274667d7f76c497293229d (diff)
Dep/efsw: updated efsw to newest version (#23894)
(cherry picked from commit ed2c2941a74ec720c5e4db3cb33367235e6c3655)
Diffstat (limited to 'dep/efsw')
-rw-r--r--dep/efsw/.hg_archival.txt7
-rw-r--r--dep/efsw/CMakeLists.txt62
-rw-r--r--dep/efsw/README.md85
-rw-r--r--dep/efsw/include/efsw/efsw.hpp6
-rw-r--r--dep/efsw/src/efsw/DirWatcherGeneric.cpp8
-rw-r--r--dep/efsw/src/efsw/DirectorySnapshot.cpp2
-rw-r--r--dep/efsw/src/efsw/FileInfo.cpp13
-rw-r--r--dep/efsw/src/efsw/FileInfo.hpp8
-rw-r--r--dep/efsw/src/efsw/FileSystem.cpp10
-rw-r--r--dep/efsw/src/efsw/FileSystem.hpp4
-rw-r--r--dep/efsw/src/efsw/FileWatcherCWrapper.cpp15
-rw-r--r--dep/efsw/src/efsw/FileWatcherFSEvents.cpp42
-rw-r--r--dep/efsw/src/efsw/FileWatcherFSEvents.hpp4
-rw-r--r--dep/efsw/src/efsw/FileWatcherGeneric.cpp44
-rw-r--r--dep/efsw/src/efsw/FileWatcherInotify.cpp131
-rw-r--r--dep/efsw/src/efsw/FileWatcherInotify.hpp2
-rw-r--r--dep/efsw/src/efsw/FileWatcherKqueue.cpp48
-rw-r--r--dep/efsw/src/efsw/FileWatcherWin32.cpp182
-rw-r--r--dep/efsw/src/efsw/FileWatcherWin32.hpp21
-rw-r--r--dep/efsw/src/efsw/Lock.hpp27
-rw-r--r--dep/efsw/src/efsw/WatcherFSEvents.cpp12
-rw-r--r--dep/efsw/src/efsw/WatcherWin32.cpp8
-rw-r--r--dep/efsw/src/efsw/base.hpp7
-rw-r--r--dep/efsw/src/efsw/inotify-nosys.h5
-rw-r--r--dep/efsw/src/efsw/platform/posix/FileSystemImpl.cpp153
-rw-r--r--dep/efsw/src/efsw/platform/posix/FileSystemImpl.hpp4
-rw-r--r--dep/efsw/src/efsw/platform/win/FileSystemImpl.cpp35
-rw-r--r--dep/efsw/src/efsw/platform/win/FileSystemImpl.hpp4
-rw-r--r--dep/efsw/src/efsw/platform/win/ThreadImpl.cpp8
-rw-r--r--dep/efsw/src/efsw/platform/win/ThreadImpl.hpp2
30 files changed, 631 insertions, 328 deletions
diff --git a/dep/efsw/.hg_archival.txt b/dep/efsw/.hg_archival.txt
index 19565afb668..f590482107c 100644
--- a/dep/efsw/.hg_archival.txt
+++ b/dep/efsw/.hg_archival.txt
@@ -1,5 +1,6 @@
repo: 78c2ea8c48b213ee0078d6326a1dd719d0844764
-node: ff0b69daeca1edf7785a8a580518e462be5a6f3d
+node: e6afbec564e249771046c714b0c7f2154e4c7fef
branch: default
-latesttag: null
-latesttagdistance: 144
+latesttag: 1.0.0
+latesttagdistance: 12
+changessincelatesttag: 12
diff --git a/dep/efsw/CMakeLists.txt b/dep/efsw/CMakeLists.txt
index b37e5021e0a..03f6c153115 100644
--- a/dep/efsw/CMakeLists.txt
+++ b/dep/efsw/CMakeLists.txt
@@ -18,50 +18,48 @@ if (BUILD_SHARED_LIBS)
src/efsw/Watcher.cpp
src/efsw/WatcherGeneric.cpp)
- if(WIN32)
- list(APPEND SRCS
+ if (WIN32)
+ list (APPEND SRCS
src/efsw/platform/win/FileSystemImpl.cpp
src/efsw/platform/win/MutexImpl.cpp
src/efsw/platform/win/SystemImpl.cpp
src/efsw/platform/win/ThreadImpl.cpp)
- else()
- list(APPEND SRCS
+ else ()
+ list (APPEND SRCS
src/efsw/platform/posix/FileSystemImpl.cpp
src/efsw/platform/posix/MutexImpl.cpp
src/efsw/platform/posix/SystemImpl.cpp
src/efsw/platform/posix/ThreadImpl.cpp)
endif()
- if (WIN32)
- list(APPEND SRCS
- src/efsw/WatcherWin32.cpp
- src/efsw/FileWatcherWin32.cpp)
+ if (APPLE)
+ list (APPEND SRCS
+ src/efsw/FileWatcherFSEvents.cpp
+ src/efsw/FileWatcherKqueue.cpp
+ src/efsw/WatcherFSEvents.cpp
+ src/efsw/WatcherKqueue.cpp)
+
+ exec_program(uname ARGS -v OUTPUT_VARIABLE OSX_VERSION)
+ string(REGEX MATCH "[0-9]+" OSX_VERSION ${OSX_VERSION})
+ if (NOT OSX_VERSION GREATER 9)
+ set(OPTIONAL_COMPILE_DEFINITIONS "-DEFSW_FSEVENTS_NOT_SUPPORTED")
+ endif()
+ set(OPTIONAL_LINK_LIBRARIES "-framework CoreFoundation" "-framework CoreServices")
+ elseif (WIN32)
+ list (APPEND SRCS
+ src/efsw/FileWatcherWin32.cpp
+ src/efsw/WatcherWin32.cpp)
elseif (${CMAKE_SYSTEM_NAME} MATCHES "Linux")
- list(APPEND SRCS
+ list (APPEND SRCS
src/efsw/FileWatcherInotify.cpp
src/efsw/WatcherInotify.cpp)
-
if (NOT EXISTS "/usr/include/sys/inotify.h" AND NOT EXISTS "/usr/local/include/sys/inotify.h")
- add_definitions(-DEFSW_INOTIFY_NOSYS)
+ set(OPTIONAL_COMPILE_DEFINITIONS "-DEFSW_INOTIFY_NOSYS")
endif()
- elseif (${CMAKE_SYSTEM_NAME} MATCHES "FreeBSD" OR APPLE)
- list(APPEND SRCS
+ elseif (${CMAKE_SYSTEM_NAME} MATCHES "FreeBSD")
+ list (APPEND SRCS
src/efsw/FileWatcherKqueue.cpp
src/efsw/WatcherKqueue.cpp)
-
- if (APPLE)
- list(APPEND SRCS
- src/efsw/FileWatcherFSEvents.cpp
- src/efsw/WatcherFSEvents.cpp)
-
- exec_program(uname ARGS -v OUTPUT_VARIABLE OSX_VERSION)
- string(REGEX MATCH "[0-9]+" OSX_VERSION ${OSX_VERSION})
- if (NOT OSX_VERSION GREATER 9)
- add_definitions(-DEFSW_FSEVENTS_NOT_SUPPORTED)
- endif()
-
- set(OPTIONAL_MAC_LINK_LIBRARIES "-framework CoreFoundation" "-framework CoreServices")
- endif()
endif()
add_library(efsw STATIC ${SRCS})
@@ -72,17 +70,21 @@ if (BUILD_SHARED_LIBS)
PRIVATE
${CMAKE_CURRENT_SOURCE_DIR}/src)
+ target_compile_definitions(efsw
+ PRIVATE
+ ${OPTIONAL_COMPILE_DEFINITIONS})
+
target_link_libraries(efsw
PRIVATE
trinity-dependency-interface
PUBLIC
threads
- ${OPTIONAL_MAC_LINK_LIBRARIES})
+ ${OPTIONAL_LINK_LIBRARIES})
set_target_properties(efsw
PROPERTIES
FOLDER
"dep")
-else()
+else ()
add_library(efsw INTERFACE IMPORTED GLOBAL)
-endif()
+endif ()
diff --git a/dep/efsw/README.md b/dep/efsw/README.md
index fda0bb599aa..f653088d575 100644
--- a/dep/efsw/README.md
+++ b/dep/efsw/README.md
@@ -29,57 +29,58 @@ This should never happen, except for the Kqueue implementation, see `Platform li
**Some example code:**
--------------------
- :::c++
- // Inherits from the abstract listener class, and implements the the file action handler
- class UpdateListener : public efsw::FileWatchListener
+```c++
+// Inherits from the abstract listener class, and implements the the file action handler
+class UpdateListener : public efsw::FileWatchListener
+{
+public:
+ UpdateListener() {}
+
+ void handleFileAction( efsw::WatchID watchid, const std::string& dir, const std::string& filename, efsw::Action action, std::string oldFilename = "" )
{
- public:
- UpdateListener() {}
-
- void handleFileAction( efsw::WatchID watchid, const std::string& dir, const std::string& filename, efsw::Action action, std::string oldFilename = "" )
+ switch( action )
{
- switch( action )
- {
- case efsw::Actions::Add:
- std::cout << "DIR (" << dir << ") FILE (" << filename << ") has event Added" << std::endl;
- break;
- case efsw::Actions::Delete:
- std::cout << "DIR (" << dir << ") FILE (" << filename << ") has event Delete" << std::endl;
- break;
- case efsw::Actions::Modified:
- std::cout << "DIR (" << dir << ") FILE (" << filename << ") has event Modified" << std::endl;
- break;
- case efsw::Actions::Moved:
- std::cout << "DIR (" << dir << ") FILE (" << filename << ") has event Moved from (" << oldFilename << ")" << std::endl;
- break;
- default:
- std::cout << "Should never happen!" << std::endl;
- }
+ case efsw::Actions::Add:
+ std::cout << "DIR (" << dir << ") FILE (" << filename << ") has event Added" << std::endl;
+ break;
+ case efsw::Actions::Delete:
+ std::cout << "DIR (" << dir << ") FILE (" << filename << ") has event Delete" << std::endl;
+ break;
+ case efsw::Actions::Modified:
+ std::cout << "DIR (" << dir << ") FILE (" << filename << ") has event Modified" << std::endl;
+ break;
+ case efsw::Actions::Moved:
+ std::cout << "DIR (" << dir << ") FILE (" << filename << ") has event Moved from (" << oldFilename << ")" << std::endl;
+ break;
+ default:
+ std::cout << "Should never happen!" << std::endl;
}
- };
+ }
+};
+
+// Create the file system watcher instance
+// efsw::FileWatcher allow a first boolean parameter that indicates if it should start with the generic file watcher instead of the platform specific backend
+efsw::FileWatcher * fileWatcher = new efsw::FileWatcher();
- // Create the file system watcher instance
- // efsw::FileWatcher allow a first boolean parameter that indicates if it should start with the generic file watcher instead of the platform specific backend
- efsw::FileWatcher * fileWatcher = new efsw::FileWatcher();
+// Create the instance of your efsw::FileWatcherListener implementation
+UpdateListener * listener = new UpdateListener();
- // Create the instance of your efsw::FileWatcherListener implementation
- UpdateListener * listener = new UpdateListener();
+// Add a folder to watch, and get the efsw::WatchID
+// It will watch the /tmp folder recursively ( the third parameter indicates that is recursive )
+// Reporting the files and directories changes to the instance of the listener
+efsw::WatchID watchID = fileWatcher->addWatch( "/tmp", listener, true );
- // Add a folder to watch, and get the efsw::WatchID
- // It will watch the /tmp folder recursively ( the third parameter indicates that is recursive )
- // Reporting the files and directories changes to the instance of the listener
- efsw::WatchID watchID = fileWatcher->addWatch( "/tmp", listener, true );
+// Adds another directory to watch. This time as non-recursive.
+efsw::WatchID watchID2 = fileWatcher->addWatch( "/usr", listener, false );
- // Adds another directory to watch. This time as non-recursive.
- efsw::WatchID watchID2 = fileWatcher->addWatch( "/usr", listener, false );
+// Start watching asynchronously the directories
+fileWatcher->watch();
- // Start watching asynchronously the directories
- fileWatcher.watch();
+// Remove the second watcher added
+// You can also call removeWatch by passing the watch path ( it must end with an slash or backslash in windows, since that's how internally it's saved )
+fileWatcher->removeWatch( watchID2 );
+```
- // Remove the second watcher added
- // You can also call removeWatch by passing the watch path ( it must end with an slash or backslash in windows, since that's how internally it's saved )
- fileWatcher->removeWatch( watchID2 );
-
**Dependencies**
--------------
None :)
diff --git a/dep/efsw/include/efsw/efsw.hpp b/dep/efsw/include/efsw/efsw.hpp
index 0693bb296f0..72ae1a61d7c 100644
--- a/dep/efsw/include/efsw/efsw.hpp
+++ b/dep/efsw/include/efsw/efsw.hpp
@@ -121,7 +121,7 @@ class EFSW_API FileWatcher
FileWatcher();
/// Constructor that lets you force the use of the Generic File Watcher
- FileWatcher( bool useGenericFileWatcher );
+ explicit FileWatcher( bool useGenericFileWatcher );
virtual ~FileWatcher();
@@ -178,10 +178,6 @@ class EFSW_API FileWatcher
class FileWatchListener
{
public:
- FileWatchListener() {}
-
- virtual ~FileWatchListener() {}
-
/// Handles the action file action
/// @param watchid The watch id for the directory
/// @param dir The directory
diff --git a/dep/efsw/src/efsw/DirWatcherGeneric.cpp b/dep/efsw/src/efsw/DirWatcherGeneric.cpp
index b80c14d24ce..a5751148863 100644
--- a/dep/efsw/src/efsw/DirWatcherGeneric.cpp
+++ b/dep/efsw/src/efsw/DirWatcherGeneric.cpp
@@ -58,7 +58,7 @@ DirWatcherGeneric::~DirWatcherGeneric()
DirWatchMap::iterator it = Directories.begin();
- for ( ; it != Directories.end(); it++ )
+ for ( ; it != Directories.end(); ++it )
{
if ( Deleted )
{
@@ -218,7 +218,7 @@ void DirWatcherGeneric::watch( bool reportOwnChange )
}
/// Process the subdirectories looking for changes
- for ( DirWatchMap::iterator dit = Directories.begin(); dit != Directories.end(); dit++ )
+ for ( DirWatchMap::iterator dit = Directories.begin(); dit != Directories.end(); ++dit )
{
/// Just watch
dit->second->watch();
@@ -293,7 +293,7 @@ DirWatcherGeneric * DirWatcherGeneric::findDirWatcher( std::string dir )
{
DirWatcherGeneric * watcher = NULL;
- for ( DirWatchMap::iterator it = Directories.begin(); it != Directories.end(); it++ )
+ for ( DirWatchMap::iterator it = Directories.begin(); it != Directories.end(); ++it )
{
watcher = it->second->findDirWatcher( dir );
@@ -437,7 +437,7 @@ bool DirWatcherGeneric::pathInWatches( std::string path )
return true;
}
- for ( DirWatchMap::iterator it = Directories.begin(); it != Directories.end(); it++ )
+ for ( DirWatchMap::iterator it = Directories.begin(); it != Directories.end(); ++it )
{
if ( it->second->pathInWatches( path ) )
{
diff --git a/dep/efsw/src/efsw/DirectorySnapshot.cpp b/dep/efsw/src/efsw/DirectorySnapshot.cpp
index c0ef747548a..e0680483e6b 100644
--- a/dep/efsw/src/efsw/DirectorySnapshot.cpp
+++ b/dep/efsw/src/efsw/DirectorySnapshot.cpp
@@ -44,6 +44,8 @@ void DirectorySnapshot::deleteAll( DirectorySnapshotDiff& Diff )
Diff.FilesDeleted.push_back( fi );
}
}
+
+ Files.clear();
}
void DirectorySnapshot::setDirectoryInfo( std::string directory )
diff --git a/dep/efsw/src/efsw/FileInfo.cpp b/dep/efsw/src/efsw/FileInfo.cpp
index 7003afc2a15..f5518225b48 100644
--- a/dep/efsw/src/efsw/FileInfo.cpp
+++ b/dep/efsw/src/efsw/FileInfo.cpp
@@ -180,22 +180,27 @@ bool FileInfo::operator==( const FileInfo& Other ) const
);
}
-bool FileInfo::isDirectory()
+bool FileInfo::isDirectory() const
{
return 0 != S_ISDIR(Permissions);
}
-bool FileInfo::isRegularFile()
+bool FileInfo::isRegularFile() const
{
return 0 != S_ISREG(Permissions);
}
-bool FileInfo::isReadable()
+bool FileInfo::isReadable() const
{
+#if EFSW_PLATFORM != EFSW_PLATFORM_WIN32
+ static bool isRoot = getuid() == 0;
+ return isRoot || 0 != S_ISRDBL(Permissions);
+#else
return 0 != S_ISRDBL(Permissions);
+#endif
}
-bool FileInfo::isLink()
+bool FileInfo::isLink() const
{
#if EFSW_PLATFORM != EFSW_PLATFORM_WIN32
return S_ISLNK(Permissions);
diff --git a/dep/efsw/src/efsw/FileInfo.hpp b/dep/efsw/src/efsw/FileInfo.hpp
index 45cca6a7953..c86e5749a70 100644
--- a/dep/efsw/src/efsw/FileInfo.hpp
+++ b/dep/efsw/src/efsw/FileInfo.hpp
@@ -29,15 +29,15 @@ class FileInfo
FileInfo& operator=( const FileInfo& Other );
- bool isDirectory();
+ bool isDirectory() const;
- bool isRegularFile();
+ bool isRegularFile() const;
- bool isReadable();
+ bool isReadable() const;
bool sameInode( const FileInfo& Other ) const;
- bool isLink();
+ bool isLink() const;
std::string linksTo();
diff --git a/dep/efsw/src/efsw/FileSystem.cpp b/dep/efsw/src/efsw/FileSystem.cpp
index e3afa0b4046..1bca40558c6 100644
--- a/dep/efsw/src/efsw/FileSystem.cpp
+++ b/dep/efsw/src/efsw/FileSystem.cpp
@@ -121,4 +121,14 @@ bool FileSystem::isRemoteFS( const std::string& directory )
return Platform::FileSystem::isRemoteFS( directory );
}
+bool FileSystem::changeWorkingDirectory( const std::string& directory )
+{
+ return Platform::FileSystem::changeWorkingDirectory( directory );
+}
+
+std::string FileSystem::getCurrentWorkingDirectory()
+{
+ return Platform::FileSystem::getCurrentWorkingDirectory();
+}
+
}
diff --git a/dep/efsw/src/efsw/FileSystem.hpp b/dep/efsw/src/efsw/FileSystem.hpp
index 4e2e1aeb7cd..07c7ade8baa 100644
--- a/dep/efsw/src/efsw/FileSystem.hpp
+++ b/dep/efsw/src/efsw/FileSystem.hpp
@@ -33,6 +33,10 @@ class FileSystem
static std::string precomposeFileName(const std::string& name);
static bool isRemoteFS( const std::string& directory );
+
+ static bool changeWorkingDirectory( const std::string & path );
+
+ static std::string getCurrentWorkingDirectory();
};
}
diff --git a/dep/efsw/src/efsw/FileWatcherCWrapper.cpp b/dep/efsw/src/efsw/FileWatcherCWrapper.cpp
index 2739e756bb2..30a36eacc35 100644
--- a/dep/efsw/src/efsw/FileWatcherCWrapper.cpp
+++ b/dep/efsw/src/efsw/FileWatcherCWrapper.cpp
@@ -12,12 +12,11 @@ public:
efsw_pfn_fileaction_callback mFn;
void* mParam;
public:
- Watcher_CAPI(efsw_watcher watcher, efsw_pfn_fileaction_callback fn, void* param)
- {
- mWatcher = watcher;
- mFn = fn;
- mParam = param;
- }
+ Watcher_CAPI(efsw_watcher watcher, efsw_pfn_fileaction_callback fn, void* param) :
+ mWatcher( watcher ),
+ mFn( fn ),
+ mParam( param )
+ {}
void handleFileAction(efsw::WatchID watchid, const std::string& dir, const std::string& filename,
efsw::Action action, std::string oldFilename = "")
@@ -34,7 +33,7 @@ static std::vector<Watcher_CAPI*> g_callbacks;
Watcher_CAPI* find_callback(efsw_watcher watcher, efsw_pfn_fileaction_callback fn)
{
- for (std::vector<Watcher_CAPI*>::iterator i = g_callbacks.begin(); i != g_callbacks.end(); i++ )
+ for (std::vector<Watcher_CAPI*>::iterator i = g_callbacks.begin(); i != g_callbacks.end(); ++i )
{
Watcher_CAPI* callback = *i;
@@ -55,7 +54,7 @@ Watcher_CAPI* remove_callback(efsw_watcher watcher)
if (callback->mWatcher == watcher)
i = g_callbacks.erase(i);
else
- i++;
+ ++i;
}
return NULL;
diff --git a/dep/efsw/src/efsw/FileWatcherFSEvents.cpp b/dep/efsw/src/efsw/FileWatcherFSEvents.cpp
index 40156674132..5aac14282c9 100644
--- a/dep/efsw/src/efsw/FileWatcherFSEvents.cpp
+++ b/dep/efsw/src/efsw/FileWatcherFSEvents.cpp
@@ -3,6 +3,7 @@
#include <efsw/System.hpp>
#include <efsw/Debug.hpp>
#include <efsw/String.hpp>
+#include <efsw/Lock.hpp>
#if EFSW_PLATFORM == EFSW_PLATFORM_FSEVENTS
@@ -14,11 +15,11 @@ namespace efsw
int getOSXReleaseNumber()
{
static int osxR = -1;
-
+
if ( -1 == osxR )
{
struct utsname os;
-
+
if ( -1 != uname( &os ) ) {
std::string release( os.release );
@@ -83,6 +84,10 @@ FileWatcherFSEvents::FileWatcherFSEvents( FileWatcher * parent ) :
FileWatcherFSEvents::~FileWatcherFSEvents()
{
+ mInitOK = false;
+
+ efSAFE_DELETE( mThread );
+
WatchMap::iterator iter = mWatches.begin();
for( ; iter != mWatches.end(); ++iter )
@@ -93,15 +98,6 @@ FileWatcherFSEvents::~FileWatcherFSEvents()
}
mWatches.clear();
-
- mInitOK = false;
-
- if ( NULL != mRunLoopRef )
- {
- CFRunLoopStop( mRunLoopRef );
- }
-
- efSAFE_DELETE( mThread );
}
WatchID FileWatcherFSEvents::addWatch( const std::string& directory, FileWatchListener* watcher, bool recursive )
@@ -165,16 +161,15 @@ WatchID FileWatcherFSEvents::addWatch( const std::string& directory, FileWatchLi
pWatch->init();
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
mWatches.insert(std::make_pair(mLastWatchID, pWatch));
- mWatchesLock.unlock();
return pWatch->ID;
}
void FileWatcherFSEvents::removeWatch(const std::string& directory)
{
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
WatchMap::iterator iter = mWatches.begin();
@@ -186,13 +181,11 @@ void FileWatcherFSEvents::removeWatch(const std::string& directory)
return;
}
}
-
- mWatchesLock.unlock();
}
void FileWatcherFSEvents::removeWatch(WatchID watchid)
{
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
WatchMap::iterator iter = mWatches.find( watchid );
@@ -206,8 +199,6 @@ void FileWatcherFSEvents::removeWatch(WatchID watchid)
efDEBUG( "Removed watch %s\n", watch->Directory.c_str() );
efSAFE_DELETE( watch );
-
- mWatchesLock.unlock();
}
void FileWatcherFSEvents::watch()
@@ -227,7 +218,7 @@ void FileWatcherFSEvents::run()
{
if ( !mNeedInit.empty() )
{
- for ( std::list<WatcherFSEvents*>::iterator it = mNeedInit.begin(); it != mNeedInit.end(); it++ )
+ for ( std::list<WatcherFSEvents*>::iterator it = mNeedInit.begin(); it != mNeedInit.end(); ++it )
{
(*it)->initAsync();
}
@@ -237,6 +228,9 @@ void FileWatcherFSEvents::run()
CFRunLoopRunInMode( kCFRunLoopDefaultMode, 0.5, kCFRunLoopRunTimedOut );
}
+
+ CFRunLoopStop( mRunLoopRef );
+ mRunLoopRef = NULL;
}
void FileWatcherFSEvents::handleAction(Watcher* watch, const std::string& filename, unsigned long action, std::string oldFilename)
@@ -248,21 +242,19 @@ std::list<std::string> FileWatcherFSEvents::directories()
{
std::list<std::string> dirs;
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
- for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); it++ )
+ for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
{
dirs.push_back( std::string( it->second->Directory ) );
}
- mWatchesLock.unlock();
-
return dirs;
}
bool FileWatcherFSEvents::pathInWatches( const std::string& path )
{
- for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); it++ )
+ for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
{
if ( it->second->Directory == path )
{
diff --git a/dep/efsw/src/efsw/FileWatcherFSEvents.hpp b/dep/efsw/src/efsw/FileWatcherFSEvents.hpp
index 6aafbc0b5ea..9a2c956ed10 100644
--- a/dep/efsw/src/efsw/FileWatcherFSEvents.hpp
+++ b/dep/efsw/src/efsw/FileWatcherFSEvents.hpp
@@ -33,9 +33,7 @@ enum FSEventEvents
efswFSEventStreamEventFlagItemIsSymlink = 0x00040000,
efswFSEventsModified = efswFSEventStreamEventFlagItemFinderInfoMod |
efswFSEventStreamEventFlagItemModified |
- efswFSEventStreamEventFlagItemInodeMetaMod |
- efswFSEventStreamEventFlagItemChangeOwner |
- efswFSEventStreamEventFlagItemXattrMod
+ efswFSEventStreamEventFlagItemInodeMetaMod
};
/// Implementation for Win32 based on ReadDirectoryChangesW.
diff --git a/dep/efsw/src/efsw/FileWatcherGeneric.cpp b/dep/efsw/src/efsw/FileWatcherGeneric.cpp
index 1534b6a9279..fd423b1476b 100644
--- a/dep/efsw/src/efsw/FileWatcherGeneric.cpp
+++ b/dep/efsw/src/efsw/FileWatcherGeneric.cpp
@@ -1,6 +1,7 @@
#include <efsw/FileWatcherGeneric.hpp>
#include <efsw/FileSystem.hpp>
#include <efsw/System.hpp>
+#include <efsw/Lock.hpp>
namespace efsw
{
@@ -18,14 +19,12 @@ FileWatcherGeneric::~FileWatcherGeneric()
{
mInitOK = false;
- mThread->wait();
-
efSAFE_DELETE( mThread );
/// Delete the watches
WatchList::iterator it = mWatches.begin();
- for ( ; it != mWatches.end(); it++ )
+ for ( ; it != mWatches.end(); ++it )
{
efSAFE_DELETE( (*it) );
}
@@ -75,9 +74,8 @@ WatchID FileWatcherGeneric::addWatch(const std::string& directory, FileWatchList
WatcherGeneric * pWatch = new WatcherGeneric( mLastWatchID, dir, watcher, this, recursive );
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
mWatches.push_back(pWatch);
- mWatchesLock.unlock();
return pWatch->ID;
}
@@ -86,20 +84,18 @@ void FileWatcherGeneric::removeWatch( const std::string& directory )
{
WatchList::iterator it = mWatches.begin();
- for ( ; it != mWatches.end(); it++ )
+ for ( ; it != mWatches.end(); ++it )
{
if ( (*it)->Directory == directory )
{
WatcherGeneric * watch = (*it);
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
mWatches.erase( it );
efSAFE_DELETE( watch ) ;
- mWatchesLock.unlock();
-
return;
}
}
@@ -109,20 +105,18 @@ void FileWatcherGeneric::removeWatch(WatchID watchid)
{
WatchList::iterator it = mWatches.begin();
- for ( ; it != mWatches.end(); it++ )
+ for ( ; it != mWatches.end(); ++it )
{
if ( (*it)->ID == watchid )
{
WatcherGeneric * watch = (*it);
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
mWatches.erase( it );
efSAFE_DELETE( watch ) ;
- mWatchesLock.unlock();
-
return;
}
}
@@ -141,22 +135,22 @@ void FileWatcherGeneric::run()
{
do
{
- mWatchesLock.lock();
+ {
+ Lock lock( mWatchesLock);
- WatchList::iterator it = mWatches.begin();
+ WatchList::iterator it = mWatches.begin();
- for ( ; it != mWatches.end(); it++ )
- {
- (*it)->watch();
+ for ( ; it != mWatches.end(); ++it )
+ {
+ ( *it )->watch();
+ }
}
- mWatchesLock.unlock();
-
if ( mInitOK ) System::sleep( 1000 );
} while ( mInitOK );
}
-void FileWatcherGeneric::handleAction(Watcher * watch, const std::string& filename, unsigned long action, std::string oldFilename)
+void FileWatcherGeneric::handleAction(Watcher *, const std::string&, unsigned long, std::string)
{
/// Not used
}
@@ -165,17 +159,15 @@ std::list<std::string> FileWatcherGeneric::directories()
{
std::list<std::string> dirs;
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
WatchList::iterator it = mWatches.begin();
- for ( ; it != mWatches.end(); it++ )
+ for ( ; it != mWatches.end(); ++it )
{
dirs.push_back( (*it)->Directory );
}
- mWatchesLock.unlock();
-
return dirs;
}
@@ -183,7 +175,7 @@ bool FileWatcherGeneric::pathInWatches( const std::string& path )
{
WatchList::iterator it = mWatches.begin();
- for ( ; it != mWatches.end(); it++ )
+ for ( ; it != mWatches.end(); ++it )
{
if ( (*it)->Directory == path || (*it)->pathInWatches( path ) )
{
diff --git a/dep/efsw/src/efsw/FileWatcherInotify.cpp b/dep/efsw/src/efsw/FileWatcherInotify.cpp
index 19c20761663..71ae3bcd97d 100644
--- a/dep/efsw/src/efsw/FileWatcherInotify.cpp
+++ b/dep/efsw/src/efsw/FileWatcherInotify.cpp
@@ -18,6 +18,8 @@
#include <efsw/FileSystem.hpp>
#include <efsw/System.hpp>
#include <efsw/Debug.hpp>
+#include <efsw/Lock.hpp>
+#include <efsw/String.hpp>
#define BUFF_SIZE ((sizeof(struct inotify_event)+FILENAME_MAX)*1024)
@@ -145,9 +147,10 @@ WatchID FileWatcherInotify::addWatch( const std::string& directory, FileWatchLis
pWatch->Recursive = recursive;
pWatch->Parent = parent;
- mWatchesLock.lock();
- mWatches.insert(std::make_pair(wd, pWatch));
- mWatchesLock.unlock();
+ {
+ Lock lock( mWatchesLock );
+ mWatches.insert(std::make_pair(wd, pWatch));
+ }
if ( NULL == pWatch->Parent )
{
@@ -159,13 +162,13 @@ WatchID FileWatcherInotify::addWatch( const std::string& directory, FileWatchLis
std::map<std::string, FileInfo> files = FileSystem::filesInfoFromPath( pWatch->Directory );
std::map<std::string, FileInfo>::iterator it = files.begin();
- for ( ; it != files.end(); it++ )
+ for ( ; it != files.end(); ++it )
{
- FileInfo fi = it->second;
+ const FileInfo& cfi = it->second;
- if ( fi.isDirectory() && fi.isReadable() )
+ if ( cfi.isDirectory() && cfi.isReadable() )
{
- addWatch( fi.Filepath, watcher, recursive, pWatch );
+ addWatch( cfi.Filepath, watcher, recursive, pWatch );
}
}
}
@@ -194,7 +197,7 @@ void FileWatcherInotify::removeWatchLocked(WatchID watchid)
}
}
- for ( std::list<WatchID>::iterator eit = eraseWatches.begin(); eit != eraseWatches.end(); eit++ )
+ for ( std::list<WatchID>::iterator eit = eraseWatches.begin(); eit != eraseWatches.end(); ++eit )
{
removeWatch( *eit );
}
@@ -228,7 +231,7 @@ void FileWatcherInotify::removeWatchLocked(WatchID watchid)
void FileWatcherInotify::removeWatch(const std::string& directory)
{
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
WatchMap::iterator iter = mWatches.begin();
@@ -251,7 +254,7 @@ void FileWatcherInotify::removeWatch(const std::string& directory)
}
}
- for ( std::list<WatchID>::iterator eit = eraseWatches.begin(); eit != eraseWatches.end(); eit++ )
+ for ( std::list<WatchID>::iterator eit = eraseWatches.begin(); eit != eraseWatches.end(); ++eit )
{
removeWatchLocked( *eit );
}
@@ -285,26 +288,20 @@ void FileWatcherInotify::removeWatch(const std::string& directory)
break;
}
}
-
- mWatchesLock.unlock();
}
void FileWatcherInotify::removeWatch( WatchID watchid )
{
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
WatchMap::iterator iter = mWatches.find( watchid );
if( iter == mWatches.end() )
{
- mWatchesLock.unlock();
-
return;
}
removeWatchLocked( watchid );
-
- mWatchesLock.unlock();
}
void FileWatcherInotify::watch()
@@ -316,6 +313,25 @@ void FileWatcherInotify::watch()
}
}
+Watcher * FileWatcherInotify::watcherContainsDirectory( std::string dir )
+{
+ FileSystem::dirRemoveSlashAtEnd( dir );
+ std::string watcherPath = FileSystem::pathRemoveFileName( dir );
+ FileSystem::dirAddSlashAtEnd( watcherPath );
+
+ for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
+ {
+ Watcher * watcher = it->second;
+
+ if ( watcher->Directory == watcherPath )
+ {
+ return watcher;
+ }
+ }
+
+ return NULL;
+}
+
void FileWatcherInotify::run()
{
static char buff[BUFF_SIZE] = {0};
@@ -333,48 +349,79 @@ void FileWatcherInotify::run()
if( select (FD_SETSIZE, &rfds, NULL, NULL, &timeout) > 0 )
{
- ssize_t len, i = 0;
+ ssize_t len;
len = read (mFD, buff, BUFF_SIZE);
if (len != -1)
{
+ ssize_t i = 0;
+
while (i < len)
{
struct inotify_event *pevent = (struct inotify_event *)&buff[i];
- mWatchesLock.lock();
-
- wit = mWatches.find( pevent->wd );
-
- if ( wit != mWatches.end() )
{
- handleAction(wit->second, pevent->name, pevent->mask);
+ Lock lock( mWatchesLock );
+
+ wit = mWatches.find( pevent->wd );
- /// Keep track of the IN_MOVED_FROM events to known if the IN_MOVED_TO event is also fired
- if ( !wit->second->OldFileName.empty() )
+ if ( wit != mWatches.end() )
{
- movedOutsideWatches.push_back( wit->second );
+ handleAction(wit->second, pevent->name, pevent->mask);
+
+ /// Keep track of the IN_MOVED_FROM events to know if the IN_MOVED_TO event is also fired
+ if ( !wit->second->OldFileName.empty() )
+ {
+ movedOutsideWatches.push_back( wit->second );
+ }
}
}
- mWatchesLock.unlock();
-
i += sizeof(struct inotify_event) + pevent->len;
}
if ( !movedOutsideWatches.empty() )
{
/// In case that the IN_MOVED_TO is never fired means that the file was moved to other folder
- for ( std::list<WatcherInotify*>::iterator it = movedOutsideWatches.begin(); it != movedOutsideWatches.end(); it++ )
+ for ( std::list<WatcherInotify*>::iterator it = movedOutsideWatches.begin(); it != movedOutsideWatches.end(); ++it )
{
- if ( !(*it)->OldFileName.empty() )
+ Watcher * watch = (*it);
+
+ if ( !watch->OldFileName.empty() )
{
- /// So we send a IN_DELETE event for files that where moved outside of our scope
- handleAction( *it, (*it)->OldFileName, IN_DELETE );
+ /// Check if the file move was a folder already being watched
+ std::list<Watcher*> eraseWatches;
+
+ for(; wit != mWatches.end(); ++wit)
+ {
+ Watcher * oldWatch = wit->second;
+
+ if ( oldWatch != watch &&
+ -1 != String::strStartsWith( watch->Directory + watch->OldFileName + "/", oldWatch->Directory ) )
+ {
+ eraseWatches.push_back( oldWatch );
+ }
+ }
+
+ /// Remove invalid watches
+ eraseWatches.sort();
+
+ for ( std::list<Watcher*>::reverse_iterator eit = eraseWatches.rbegin(); eit != eraseWatches.rend(); ++eit )
+ {
+ Watcher * rmWatch = *eit;
+
+ /// Create Delete event for removed watches that have been moved too
+ if ( Watcher * cntWatch = watcherContainsDirectory( rmWatch->Directory ) )
+ {
+ handleAction( cntWatch, FileSystem::fileNameFromPath( rmWatch->Directory ), IN_DELETE );
+ }
+
+ removeWatch( rmWatch->ID );
+ }
/// Remove the OldFileName
- (*it)->OldFileName = "";
+ watch->OldFileName = "";
}
}
@@ -395,7 +442,7 @@ void FileWatcherInotify::checkForNewWatcher( Watcher* watch, std::string fpath )
bool found = false;
/// First check if exists
- for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); it++ )
+ for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
{
if ( it->second->Directory == fpath )
{
@@ -411,7 +458,7 @@ void FileWatcherInotify::checkForNewWatcher( Watcher* watch, std::string fpath )
}
}
-void FileWatcherInotify::handleAction( Watcher* watch, const std::string& filename, unsigned long action, std::string oldFilename )
+void FileWatcherInotify::handleAction( Watcher* watch, const std::string& filename, unsigned long action, std::string )
{
if ( !watch || !watch->Listener )
{
@@ -447,7 +494,7 @@ void FileWatcherInotify::handleAction( Watcher* watch, const std::string& filena
FileSystem::dirAddSlashAtEnd( opath );
FileSystem::dirAddSlashAtEnd( fpath );
- for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); it++ )
+ for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
{
if ( it->second->Directory == opath && it->second->DirInfo.Inode == FileInfo( opath ).Inode )
{
@@ -480,7 +527,7 @@ void FileWatcherInotify::handleAction( Watcher* watch, const std::string& filena
/// If the file erased is a directory and recursive is enabled, removes the directory erased
if ( watch->Recursive )
{
- for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); it++ )
+ for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
{
if ( it->second->Directory == fpath )
{
@@ -496,17 +543,15 @@ std::list<std::string> FileWatcherInotify::directories()
{
std::list<std::string> dirs;
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
WatchMap::iterator it = mRealWatches.begin();
- for ( ; it != mRealWatches.end(); it++ )
+ for ( ; it != mRealWatches.end(); ++it )
{
dirs.push_back( it->second->Directory );
}
- mWatchesLock.unlock();
-
return dirs;
}
@@ -515,7 +560,7 @@ bool FileWatcherInotify::pathInWatches( const std::string& path )
/// Search in the real watches, since it must allow adding a watch already watched as a subdir
WatchMap::iterator it = mRealWatches.begin();
- for ( ; it != mRealWatches.end(); it++ )
+ for ( ; it != mRealWatches.end(); ++it )
{
if ( it->second->Directory == path )
{
diff --git a/dep/efsw/src/efsw/FileWatcherInotify.hpp b/dep/efsw/src/efsw/FileWatcherInotify.hpp
index 43ee9ca6afc..b68314050a1 100644
--- a/dep/efsw/src/efsw/FileWatcherInotify.hpp
+++ b/dep/efsw/src/efsw/FileWatcherInotify.hpp
@@ -64,6 +64,8 @@ class FileWatcherInotify : public FileWatcherImpl
void removeWatchLocked(WatchID watchid);
void checkForNewWatcher( Watcher* watch, std::string fpath );
+
+ Watcher * watcherContainsDirectory( std::string dir );
};
}
diff --git a/dep/efsw/src/efsw/FileWatcherKqueue.cpp b/dep/efsw/src/efsw/FileWatcherKqueue.cpp
index 600fd085b35..3373a68d0ce 100644
--- a/dep/efsw/src/efsw/FileWatcherKqueue.cpp
+++ b/dep/efsw/src/efsw/FileWatcherKqueue.cpp
@@ -15,6 +15,7 @@
#include <efsw/System.hpp>
#include <efsw/Debug.hpp>
#include <efsw/WatcherGeneric.hpp>
+#include <efsw/Lock.hpp>
namespace efsw
{
@@ -44,8 +45,6 @@ FileWatcherKqueue::~FileWatcherKqueue()
mInitOK = false;
- mThread->wait();
-
efSAFE_DELETE( mThread );
}
@@ -98,9 +97,10 @@ WatchID FileWatcherKqueue::addWatch(const std::string& directory, FileWatchListe
WatcherKqueue * watch = new WatcherKqueue( ++mLastWatchID, dir, watcher, recursive, this );
- mWatchesLock.lock();
- mWatches.insert(std::make_pair(mLastWatchID, watch));
- mWatchesLock.unlock();
+ {
+ Lock lock( mWatchesLock );
+ mWatches.insert(std::make_pair(mLastWatchID, watch));
+ }
watch->addAll();
@@ -118,11 +118,10 @@ WatchID FileWatcherKqueue::addWatch(const std::string& directory, FileWatchListe
// Probably the folder has too many files, create a generic watcher
if ( EACCES != le )
{
- WatcherGeneric * watch = new WatcherGeneric( ++mLastWatchID, dir, watcher, this, recursive );
+ WatcherGeneric * genericWatch = new WatcherGeneric( ++mLastWatchID, dir, watcher, this, recursive );
- mWatchesLock.lock();
- mWatches.insert(std::make_pair(mLastWatchID, watch));
- mWatchesLock.unlock();
+ Lock lock( mWatchesLock );
+ mWatches.insert(std::make_pair(mLastWatchID, genericWatch));
}
else
{
@@ -142,9 +141,8 @@ WatchID FileWatcherKqueue::addWatch(const std::string& directory, FileWatchListe
WatcherGeneric * watch = new WatcherGeneric( ++mLastWatchID, dir, watcher, this, recursive );
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
mWatches.insert(std::make_pair(mLastWatchID, watch));
- mWatchesLock.unlock();
}
return mLastWatchID;
@@ -152,7 +150,7 @@ WatchID FileWatcherKqueue::addWatch(const std::string& directory, FileWatchListe
void FileWatcherKqueue::removeWatch(const std::string& directory)
{
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
WatchMap::iterator iter = mWatches.begin();
@@ -164,13 +162,11 @@ void FileWatcherKqueue::removeWatch(const std::string& directory)
return;
}
}
-
- mWatchesLock.unlock();
}
void FileWatcherKqueue::removeWatch(WatchID watchid)
{
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
WatchMap::iterator iter = mWatches.find(watchid);
@@ -182,8 +178,6 @@ void FileWatcherKqueue::removeWatch(WatchID watchid)
mWatches.erase(iter);
efSAFE_DELETE( watch );
-
- mWatchesLock.unlock();
}
bool FileWatcherKqueue::isAddingWatcher() const
@@ -204,14 +198,14 @@ void FileWatcherKqueue::run()
{
do
{
- mWatchesLock.lock();
-
- for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
{
- it->second->watch();
- }
+ Lock lock( mWatchesLock );
- mWatchesLock.unlock();
+ for ( WatchMap::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
+ {
+ it->second->watch();
+ }
+ }
System::sleep( 500 );
} while( mInitOK );
@@ -225,17 +219,15 @@ std::list<std::string> FileWatcherKqueue::directories()
{
std::list<std::string> dirs;
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
WatchMap::iterator it = mWatches.begin();
- for ( ; it != mWatches.end(); it++ )
+ for ( ; it != mWatches.end(); ++it )
{
dirs.push_back( it->second->Directory );
}
- mWatchesLock.unlock();
-
return dirs;
}
@@ -243,7 +235,7 @@ bool FileWatcherKqueue::pathInWatches( const std::string& path )
{
WatchMap::iterator it = mWatches.begin();
- for ( ; it != mWatches.end(); it++ )
+ for ( ; it != mWatches.end(); ++it )
{
if ( it->second->Directory == path )
{
diff --git a/dep/efsw/src/efsw/FileWatcherWin32.cpp b/dep/efsw/src/efsw/FileWatcherWin32.cpp
index fe78dd122cf..317506fb3e3 100644
--- a/dep/efsw/src/efsw/FileWatcherWin32.cpp
+++ b/dep/efsw/src/efsw/FileWatcherWin32.cpp
@@ -2,6 +2,7 @@
#include <efsw/FileSystem.hpp>
#include <efsw/System.hpp>
#include <efsw/String.hpp>
+#include <efsw/Lock.hpp>
#if EFSW_PLATFORM == EFSW_PLATFORM_WIN32
@@ -18,23 +19,9 @@ FileWatcherWin32::FileWatcherWin32( FileWatcher * parent ) :
FileWatcherWin32::~FileWatcherWin32()
{
- WatchVector::iterator iter = mWatches.begin();
-
- mWatchesLock.lock();
-
- for(; iter != mWatches.end(); ++iter)
- {
- DestroyWatch((*iter));
- }
-
- mHandles.clear();
- mWatches.clear();
-
mInitOK = false;
-
- mWatchesLock.unlock();
-
efSAFE_DELETE( mThread );
+ removeAllWatches();
}
WatchID FileWatcherWin32::addWatch(const std::string& directory, FileWatchListener* watcher, bool recursive)
@@ -54,9 +41,14 @@ WatchID FileWatcherWin32::addWatch(const std::string& directory, FileWatchListen
FileSystem::dirAddSlashAtEnd( dir );
- WatchID watchid = ++mLastWatchID;
+ Lock lock( mWatchesLock );
+
+ if ( pathInWatches( dir ) )
+ {
+ return Errors::Log::createLastError( Errors::FileRepeated, dir );
+ }
- mWatchesLock.lock();
+ WatchID watchid = ++mLastWatchID;
WatcherStructWin32 * watch = CreateWatch( String::fromUtf8( dir ).toWideString().c_str(), recursive, FILE_NOTIFY_CHANGE_CREATION |
FILE_NOTIFY_CHANGE_LAST_WRITE |
@@ -70,11 +62,6 @@ WatchID FileWatcherWin32::addWatch(const std::string& directory, FileWatchListen
return Errors::Log::createLastError( Errors::FileNotFound, dir );
}
- if ( pathInWatches( dir ) )
- {
- return Errors::Log::createLastError( Errors::FileRepeated, dir );
- }
-
// Add the handle to the handles vector
watch->Watch->ID = watchid;
watch->Watch->Watch = this;
@@ -82,67 +69,81 @@ WatchID FileWatcherWin32::addWatch(const std::string& directory, FileWatchListen
watch->Watch->DirName = new char[dir.length()+1];
strcpy(watch->Watch->DirName, dir.c_str());
- mHandles.push_back( watch->Watch->DirHandle );
- mWatches.push_back( watch );
- mWatchesLock.unlock();
+ mWatchesNew.insert( watch );
+ mWatches.insert( watch );
return watchid;
}
void FileWatcherWin32::removeWatch(const std::string& directory)
{
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
- WatchVector::iterator iter = mWatches.begin();
+ Watches::iterator iter = mWatches.begin();
for(; iter != mWatches.end(); ++iter)
{
if(directory == (*iter)->Watch->DirName)
{
- removeWatch((*iter)->Watch->ID);
- return;
+ removeWatch(*iter);
+ break;
}
}
-
- mWatchesLock.unlock();
}
void FileWatcherWin32::removeWatch(WatchID watchid)
{
- mWatchesLock.lock();
-
- WatchVector::iterator iter = mWatches.begin();
+ Lock lock( mWatchesLock );
- WatcherStructWin32* watch = NULL;
+ Watches::iterator iter = mWatches.begin();
for(; iter != mWatches.end(); ++iter)
{
// Find the watch ID
if ( (*iter)->Watch->ID == watchid )
{
- watch = (*iter);
+ removeWatch(*iter);
+ return;
+ }
+ }
+}
- mWatches.erase( iter );
+void FileWatcherWin32::removeWatch(WatcherStructWin32* watch)
+{
+ mWatchesRemoved.insert(watch);
- // Remove handle from the handle vector
- HandleVector::iterator it = mHandles.begin();
+ if( NULL == mThread )
+ {
+ removeWatches();
+ }
+}
- for ( ; it != mHandles.end(); it++ )
- {
- if ( watch->Watch->DirHandle == (*it) )
- {
- mHandles.erase( it );
- break;
- }
- }
+void FileWatcherWin32::removeWatches()
+{
+ Lock lock( mWatchesLock );
- DestroyWatch(watch);
+ Watches::iterator remWatchIter = mWatchesRemoved.begin();
- break;
+ for( ; remWatchIter != mWatchesRemoved.end(); ++remWatchIter )
+ {
+ Watches::iterator iter = mWatches.find(*remWatchIter);
+
+ if( iter != mWatches.end() )
+ {
+ DestroyWatch(*iter);
+
+ mWatches.erase( iter );
+ }
+
+ iter = mWatchesNew.find(*remWatchIter);
+
+ if( iter != mWatchesNew.end() )
+ {
+ mWatchesNew.erase( iter );
}
}
- mWatchesLock.unlock();
+ mWatchesRemoved.clear();
}
void FileWatcherWin32::watch()
@@ -154,45 +155,47 @@ void FileWatcherWin32::watch()
}
}
-void FileWatcherWin32::run()
+void FileWatcherWin32::removeAllWatches()
{
- if ( mHandles.empty() )
+ Lock lock( mWatchesLock );
+
+ Watches::iterator iter = mWatches.begin();
+
+ for( ; iter != mWatches.end(); ++iter )
{
- return;
+ DestroyWatch((*iter));
}
+ mWatches.clear();
+ mWatchesRemoved.clear();
+ mWatchesNew.clear();
+}
+
+void FileWatcherWin32::run()
+{
do
{
- if ( !mHandles.empty() )
+ if ( !mWatches.empty() )
{
- mWatchesLock.lock();
-
- for ( std::size_t i = 0; i < mWatches.size(); i++ )
{
- WatcherStructWin32 * watch = mWatches[ i ];
-
- // If the overlapped struct was cancelled ( because the creator thread doesn't exists anymore ),
- // we recreate the overlapped in the current thread and refresh the watch
- if ( /*STATUS_CANCELED*/0xC0000120 == watch->Overlapped.Internal )
- {
- watch->Overlapped = OVERLAPPED();
- RefreshWatch(watch);
- }
+ Lock lock( mWatchesLock );
- // First ensure that the handle is the same, this means that the watch was not removed.
- if ( HasOverlappedIoCompleted( &watch->Overlapped ) && mHandles[ i ] == watch->Watch->DirHandle )
+ for( Watches::iterator iter = mWatches.begin() ; iter != mWatches.end(); ++iter )
{
- DWORD bytes;
+ WatcherStructWin32 * watch = *iter;
- if ( GetOverlappedResult( watch->Watch->DirHandle, &watch->Overlapped, &bytes, FALSE ) )
+ if ( HasOverlappedIoCompleted( &watch->Overlapped ) )
{
- WatchCallback( ERROR_SUCCESS, bytes, &watch->Overlapped );
+ DWORD bytes;
+
+ if ( GetOverlappedResult( watch->Watch->DirHandle, &watch->Overlapped, &bytes, FALSE ) )
+ {
+ WatchCallback( ERROR_SUCCESS, bytes, &watch->Overlapped );
+ }
}
}
}
- mWatchesLock.unlock();
-
if ( mInitOK )
{
System::sleep( 10 );
@@ -203,7 +206,18 @@ void FileWatcherWin32::run()
// Wait for a new handle to be added
System::sleep( 10 );
}
+
+ removeWatches();
+
+ for ( Watches::iterator it = mWatchesNew.begin(); it != mWatchesNew.end(); ++it )
+ {
+ RefreshWatch(*it);
+ }
+
+ mWatchesNew.clear();
} while ( mInitOK );
+
+ removeAllWatches();
}
void FileWatcherWin32::handleAction(Watcher* watch, const std::string& filename, unsigned long action, std::string oldFilename)
@@ -232,7 +246,7 @@ void FileWatcherWin32::handleAction(Watcher* watch, const std::string& filename,
FileSystem::dirAddSlashAtEnd( opath );
FileSystem::dirAddSlashAtEnd( fpath );
- for ( WatchVector::iterator it = mWatches.begin(); it != mWatches.end(); it++ )
+ for ( Watches::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
{
if ( (*it)->Watch->Directory == opath )
{
@@ -254,28 +268,36 @@ void FileWatcherWin32::handleAction(Watcher* watch, const std::string& filename,
break;
};
- watch->Listener->handleFileAction(watch->ID, static_cast<WatcherWin32*>( watch )->DirName, filename, fwAction);
+ std::string folderPath( static_cast<WatcherWin32*>( watch )->DirName );
+ std::string realFilename = filename;
+ std::size_t sepPos = filename.find_last_of("/\\");
+
+ if ( sepPos != std::string::npos )
+ {
+ folderPath += filename.substr( 0, sepPos );
+ realFilename = filename.substr( sepPos + 1 );
+ }
+
+ watch->Listener->handleFileAction(watch->ID, folderPath, realFilename, fwAction);
}
std::list<std::string> FileWatcherWin32::directories()
{
std::list<std::string> dirs;
- mWatchesLock.lock();
+ Lock lock( mWatchesLock );
- for ( WatchVector::iterator it = mWatches.begin(); it != mWatches.end(); it++ )
+ for ( Watches::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
{
dirs.push_back( std::string( (*it)->Watch->DirName ) );
}
- mWatchesLock.unlock();
-
return dirs;
}
bool FileWatcherWin32::pathInWatches( const std::string& path )
{
- for ( WatchVector::iterator it = mWatches.begin(); it != mWatches.end(); it++ )
+ for ( Watches::iterator it = mWatches.begin(); it != mWatches.end(); ++it )
{
if ( (*it)->Watch->DirName == path )
{
diff --git a/dep/efsw/src/efsw/FileWatcherWin32.hpp b/dep/efsw/src/efsw/FileWatcherWin32.hpp
index 505cd772b82..983ee1853d0 100644
--- a/dep/efsw/src/efsw/FileWatcherWin32.hpp
+++ b/dep/efsw/src/efsw/FileWatcherWin32.hpp
@@ -6,7 +6,7 @@
#if EFSW_PLATFORM == EFSW_PLATFORM_WIN32
#include <efsw/WatcherWin32.hpp>
-#include <vector>
+#include <set>
#include <map>
namespace efsw
@@ -18,8 +18,7 @@ class FileWatcherWin32 : public FileWatcherImpl
{
public:
/// type for a map from WatchID to WatcherWin32 pointer
- typedef std::vector<WatcherStructWin32*> WatchVector;
- typedef std::vector<HANDLE> HandleVector;
+ typedef std::set<WatcherStructWin32*> Watches;
FileWatcherWin32( FileWatcher * parent );
@@ -44,11 +43,9 @@ class FileWatcherWin32 : public FileWatcherImpl
/// @return Returns a list of the directories that are being watched
std::list<std::string> directories();
protected:
- /// Vector of WatcherWin32 pointers
- WatchVector mWatches;
-
- /// Keeps an updated handles vector
- HandleVector mHandles;
+ Watches mWatches;
+ Watches mWatchesRemoved;
+ Watches mWatchesNew;
/// The last watchid
WatchID mLastWatchID;
@@ -58,6 +55,14 @@ class FileWatcherWin32 : public FileWatcherImpl
Mutex mWatchesLock;
bool pathInWatches( const std::string& path );
+
+ /// Remove all directory watches.
+ void removeAllWatches();
+
+ /// Remove needed directory watches.
+ void removeWatches();
+
+ void removeWatch(WatcherStructWin32* watch);
private:
void run();
};
diff --git a/dep/efsw/src/efsw/Lock.hpp b/dep/efsw/src/efsw/Lock.hpp
new file mode 100644
index 00000000000..5dbf11e39ce
--- /dev/null
+++ b/dep/efsw/src/efsw/Lock.hpp
@@ -0,0 +1,27 @@
+#ifndef EFSW_LOCK_HPP
+#define EFSW_LOCK_HPP
+
+#include <efsw/Mutex.hpp>
+
+namespace efsw {
+
+/** Simple mutex class */
+class Lock {
+ public:
+ explicit Lock( Mutex& mutex ) :
+ mMutex( mutex )
+ {
+ mMutex.lock();
+ }
+
+ ~Lock()
+ {
+ mMutex.unlock();
+ }
+ private:
+ Mutex& mMutex;
+};
+
+}
+
+#endif
diff --git a/dep/efsw/src/efsw/WatcherFSEvents.cpp b/dep/efsw/src/efsw/WatcherFSEvents.cpp
index 3a9700c77ec..a13a743b01e 100644
--- a/dep/efsw/src/efsw/WatcherFSEvents.cpp
+++ b/dep/efsw/src/efsw/WatcherFSEvents.cpp
@@ -27,14 +27,14 @@ WatcherFSEvents::WatcherFSEvents( WatchID id, std::string directory, FileWatchLi
WatcherFSEvents::~WatcherFSEvents()
{
- if ( initializedAsync )
- {
- FSEventStreamStop( FSStream );
- FSEventStreamInvalidate( FSStream );
- }
-
if ( NULL != FSStream )
{
+ if ( initializedAsync )
+ {
+ FSEventStreamStop( FSStream );
+ }
+
+ FSEventStreamInvalidate( FSStream );
FSEventStreamRelease( FSStream );
}
diff --git a/dep/efsw/src/efsw/WatcherWin32.cpp b/dep/efsw/src/efsw/WatcherWin32.cpp
index 01d7b0fcd99..4d2dc7e064f 100644
--- a/dep/efsw/src/efsw/WatcherWin32.cpp
+++ b/dep/efsw/src/efsw/WatcherWin32.cpp
@@ -87,15 +87,9 @@ void DestroyWatch(WatcherStructWin32* pWatch)
tWatch->StopNow = true;
- CancelIo(tWatch->DirHandle);
+ CancelIoEx(tWatch->DirHandle, &pWatch->Overlapped);
RefreshWatch(pWatch);
-
- if (!HasOverlappedIoCompleted(&pWatch->Overlapped))
- {
- SleepEx(5, TRUE);
- }
-
CloseHandle(pWatch->Overlapped.hEvent);
CloseHandle(pWatch->Watch->DirHandle);
efSAFE_DELETE_ARRAY( pWatch->Watch->DirName );
diff --git a/dep/efsw/src/efsw/base.hpp b/dep/efsw/src/efsw/base.hpp
index 26108c76985..b5a9687dc74 100644
--- a/dep/efsw/src/efsw/base.hpp
+++ b/dep/efsw/src/efsw/base.hpp
@@ -38,7 +38,12 @@ typedef SOPHIST_uint64 Uint64;
#if ( defined( _MSCVER ) || defined( _MSC_VER ) )
#define EFSW_COMPILER_MSVC
#endif
-
+
+ /// Force windows target version above or equal to Windows Server 2008 or Windows Vista
+ #if _WIN32_WINNT < 0x600
+ #undef _WIN32_WINNT
+ #define _WIN32_WINNT 0x600
+ #endif
#elif defined( __FreeBSD__ ) || defined(__OpenBSD__) || defined( __NetBSD__ ) || defined( __DragonFly__ )
#define EFSW_OS EFSW_OS_BSD
#define EFSW_PLATFORM EFSW_PLATFORM_KQUEUE
diff --git a/dep/efsw/src/efsw/inotify-nosys.h b/dep/efsw/src/efsw/inotify-nosys.h
index 75df5d3ced3..be1e627d962 100644
--- a/dep/efsw/src/efsw/inotify-nosys.h
+++ b/dep/efsw/src/efsw/inotify-nosys.h
@@ -69,6 +69,11 @@ struct inotify_event {
# define __NR_inotify_add_watch (__NR_SYSCALL_BASE+317)
# define __NR_inotify_rm_watch (__NR_SYSCALL_BASE+318)
+#elif defined (__aarch64__)
+# define __NR_inotify_init 1043
+# define __NR_inotify_add_watch 27
+# define __NR_inotify_rm_watch 28
+
#elif defined (__frv__)
# define __NR_inotify_init 291
# define __NR_inotify_add_watch 292
diff --git a/dep/efsw/src/efsw/platform/posix/FileSystemImpl.cpp b/dep/efsw/src/efsw/platform/posix/FileSystemImpl.cpp
index e061b25d56b..5795d567740 100644
--- a/dep/efsw/src/efsw/platform/posix/FileSystemImpl.cpp
+++ b/dep/efsw/src/efsw/platform/posix/FileSystemImpl.cpp
@@ -5,6 +5,7 @@
#include <efsw/FileInfo.hpp>
#include <efsw/FileSystem.hpp>
#include <dirent.h>
+#include <unistd.h>
#include <cstring>
#ifndef _DARWIN_FEATURE_64_BIT_INODE
@@ -17,6 +18,7 @@
#include <sys/stat.h>
#include <cstdlib>
+#include <climits>
#if EFSW_OS == EFSW_OS_LINUX || EFSW_OS == EFSW_OS_SOLARIS || EFSW_OS == EFSW_OS_ANDROID
#include <sys/vfs.h>
@@ -49,8 +51,152 @@
#define S_MAGIC_VMHGFS 0xBACBACBC
#define S_MAGIC_VXFS 0xA501FCF5
+#if EFSW_OS == EFSW_OS_LINUX
+#include <mntent.h>
+#include <cstdio>
+#endif
+
namespace efsw { namespace Platform {
+#if EFSW_OS == EFSW_OS_LINUX
+
+#pragma pack(push, 1)
+struct ntfs_super_block
+{
+ char jump[3];
+ char oem_id[8];
+};
+#pragma pack(pop)
+
+bool isNTFS( std::string device )
+{
+ FILE * fd = fopen( device.c_str(), "r" );
+
+ ntfs_super_block ns;
+
+ if ( fd != NULL )
+ {
+ fread( &ns, 1, sizeof(ntfs_super_block), fd );
+ fclose( fd );
+
+ std::string oemId( ns.oem_id );
+
+ return oemId.compare(0, 4, "NTFS") == 0;
+ }
+
+ return false;
+}
+
+std::string findMountPoint( std::string file )
+{
+ std::string cwd = FileSystem::getCurrentWorkingDirectory();
+ struct stat last_stat;
+ struct stat file_stat;
+
+ stat( file.c_str(), &file_stat );
+
+ std::string mp;
+
+ if ( efsw::FileSystem::isDirectory( file ) ) {
+ last_stat = file_stat;
+
+ if ( !FileSystem::changeWorkingDirectory( file ) )
+ return "";
+ } else {
+ std::string dir = efsw::FileSystem::pathRemoveFileName( file );
+
+ if ( !FileSystem::changeWorkingDirectory( dir ) )
+ return "";
+
+ if (stat (".", &last_stat) < 0)
+ return "";
+ }
+
+ while (true)
+ {
+ struct stat st;
+
+ if ( stat("..", &st) < 0 )
+ goto done;
+
+ if ( st.st_dev != last_stat.st_dev || st.st_ino == last_stat.st_ino )
+ break;
+
+ if ( !FileSystem::changeWorkingDirectory("..") )
+ {
+ goto done;
+ }
+
+ last_stat = st;
+ }
+
+ /* Finally reached a mount point, see what it's called. */
+ mp = FileSystem::getCurrentWorkingDirectory();
+
+done:
+ FileSystem::changeWorkingDirectory( cwd );
+
+ return mp;
+}
+
+std::string findDevicePath( const std::string& directory )
+{
+ struct mntent *ent;
+ FILE *aFile;
+
+ aFile = setmntent("/proc/mounts", "r");
+
+ if ( aFile == NULL )
+ return "";
+
+ while ( NULL != ( ent = getmntent( aFile ) ) )
+ {
+ std::string dirName( ent->mnt_dir );
+
+ if ( dirName == directory )
+ {
+ std::string fsName( ent->mnt_fsname );
+
+ endmntent(aFile);
+
+ return fsName;
+ }
+ }
+
+ endmntent(aFile);
+
+ return "";
+}
+
+bool isLocalFUSEDirectory( std::string directory )
+{
+ efsw::FileSystem::dirRemoveSlashAtEnd( directory );
+
+ directory = findMountPoint( directory );
+
+ if ( !directory.empty() )
+ {
+ std::string devicePath = findDevicePath( directory );
+
+ return ( !devicePath.empty() && isNTFS( devicePath ) );
+ }
+
+ return false;
+}
+
+#endif
+
+bool FileSystem::changeWorkingDirectory( const std::string & path )
+{
+ return -1 != chdir( path.c_str() );
+}
+
+std::string FileSystem::getCurrentWorkingDirectory() {
+ char dir[PATH_MAX + 1];
+ getcwd( dir, PATH_MAX + 1 );
+ return std::string( dir );
+}
+
FileInfoMap FileSystem::filesInfoFromPath( const std::string& path )
{
FileInfoMap files;
@@ -104,13 +250,18 @@ bool FileSystem::isRemoteFS( const std::string& directory )
switch ( statfsbuf.f_type | 0UL )
{
+ case S_MAGIC_FUSEBLK: /* 0x65735546 remote */
+ {
+ #if EFSW_OS == EFSW_OS_LINUX
+ return !isLocalFUSEDirectory( directory );
+ #endif
+ }
case S_MAGIC_AFS: /* 0x5346414F remote */
case S_MAGIC_AUFS: /* 0x61756673 remote */
case S_MAGIC_CEPH: /* 0x00C36400 remote */
case S_MAGIC_CIFS: /* 0xFF534D42 remote */
case S_MAGIC_CODA: /* 0x73757245 remote */
case S_MAGIC_FHGFS: /* 0x19830326 remote */
- case S_MAGIC_FUSEBLK: /* 0x65735546 remote */
case S_MAGIC_FUSECTL: /* 0x65735543 remote */
case S_MAGIC_GFS: /* 0x01161970 remote */
case S_MAGIC_GPFS: /* 0x47504653 remote */
diff --git a/dep/efsw/src/efsw/platform/posix/FileSystemImpl.hpp b/dep/efsw/src/efsw/platform/posix/FileSystemImpl.hpp
index 865b3f8dfdf..7353d81cf3f 100644
--- a/dep/efsw/src/efsw/platform/posix/FileSystemImpl.hpp
+++ b/dep/efsw/src/efsw/platform/posix/FileSystemImpl.hpp
@@ -18,6 +18,10 @@ class FileSystem
static bool isDirectory( const std::string& path );
static bool isRemoteFS( const std::string& directory );
+
+ static bool changeWorkingDirectory( const std::string & path );
+
+ static std::string getCurrentWorkingDirectory();
};
}}
diff --git a/dep/efsw/src/efsw/platform/win/FileSystemImpl.cpp b/dep/efsw/src/efsw/platform/win/FileSystemImpl.cpp
index 376a474e662..cf27eb7a0f6 100644
--- a/dep/efsw/src/efsw/platform/win/FileSystemImpl.cpp
+++ b/dep/efsw/src/efsw/platform/win/FileSystemImpl.cpp
@@ -2,6 +2,7 @@
#if EFSW_PLATFORM == EFSW_PLATFORM_WIN32
+#include <climits>
#ifndef WIN32_LEAN_AND_MEAN
#define WIN32_LEAN_AND_MEAN
#endif
@@ -9,10 +10,44 @@
#ifndef EFSW_COMPILER_MSVC
#include <dirent.h>
+#else
+#include <direct.h>
#endif
namespace efsw { namespace Platform {
+bool FileSystem::changeWorkingDirectory( const std::string & path )
+{
+ int res;
+#ifdef EFSW_COMPILER_MSVC
+ #ifdef UNICODE
+ res = _wchdir( String::fromUtf8( path.c_str() ).toWideString().c_str() );
+ #else
+ res = _chdir( String::fromUtf8( path.c_str() ).toAnsiString().c_str() );
+ #endif
+#else
+ res = chdir( path.c_str() );
+#endif
+ return -1 != res;
+}
+
+std::string FileSystem::getCurrentWorkingDirectory()
+{
+#ifdef EFSW_COMPILER_MSVC
+ #if defined( UNICODE ) AND !defined( EFSW_NO_WIDECHAR )
+ wchar_t dir[_MAX_PATH];
+ return ( 0 != GetCurrentDirectoryW( _MAX_PATH, dir ) ) ? String( dir ).toUtf8() : std::string();
+ #else
+ char dir[_MAX_PATH];
+ return ( 0 != GetCurrentDirectory( _MAX_PATH, dir ) ) ? String( dir, std::locale() ).toUtf8() : std::string();
+ #endif
+#else
+ char dir[PATH_MAX + 1];
+ getcwd( dir, PATH_MAX + 1 );
+ return std::string( dir );
+#endif
+}
+
FileInfoMap FileSystem::filesInfoFromPath( const std::string& path )
{
FileInfoMap files;
diff --git a/dep/efsw/src/efsw/platform/win/FileSystemImpl.hpp b/dep/efsw/src/efsw/platform/win/FileSystemImpl.hpp
index 597edc4a647..8f6c5ad1837 100644
--- a/dep/efsw/src/efsw/platform/win/FileSystemImpl.hpp
+++ b/dep/efsw/src/efsw/platform/win/FileSystemImpl.hpp
@@ -19,6 +19,10 @@ class FileSystem
static bool isDirectory( const std::string& path );
static bool isRemoteFS( const std::string& directory );
+
+ static bool changeWorkingDirectory( const std::string & path );
+
+ static std::string getCurrentWorkingDirectory();
};
}}
diff --git a/dep/efsw/src/efsw/platform/win/ThreadImpl.cpp b/dep/efsw/src/efsw/platform/win/ThreadImpl.cpp
index 2fa30f30060..48c9456adab 100644
--- a/dep/efsw/src/efsw/platform/win/ThreadImpl.cpp
+++ b/dep/efsw/src/efsw/platform/win/ThreadImpl.cpp
@@ -18,6 +18,14 @@ ThreadImpl::ThreadImpl( Thread *owner )
}
}
+ThreadImpl::~ThreadImpl()
+{
+ if ( mThread )
+ {
+ CloseHandle( mThread );
+ }
+}
+
void ThreadImpl::wait()
{
// Wait for the thread to finish, no timeout
diff --git a/dep/efsw/src/efsw/platform/win/ThreadImpl.hpp b/dep/efsw/src/efsw/platform/win/ThreadImpl.hpp
index 506c659c675..45e4505897a 100644
--- a/dep/efsw/src/efsw/platform/win/ThreadImpl.hpp
+++ b/dep/efsw/src/efsw/platform/win/ThreadImpl.hpp
@@ -21,6 +21,8 @@ class ThreadImpl
{
public:
ThreadImpl( Thread * owner );
+
+ ~ThreadImpl();
void wait();