1
1
#include " ../includes/win32/Controller.h"
2
2
3
+ static bool isNtPath (const std::wstring &path) {
4
+ return path.rfind (L" \\\\ ?\\ " , 0 ) == 0 || path.rfind (L" \\ ??\\ " , 0 ) == 0 ;
5
+ }
6
+
7
+ static std::wstring prefixWithNtPath (const std::wstring &path) {
8
+ const ULONG widePathLength = GetFullPathNameW (path.c_str (), 0 , nullptr , nullptr );
9
+ if (widePathLength == 0 ) {
10
+ return path;
11
+ }
12
+
13
+ std::wstring ntPathString;
14
+ ntPathString.resize (widePathLength - 1 );
15
+ if (GetFullPathNameW (path.c_str (), widePathLength, &(ntPathString[0 ]), nullptr ) != widePathLength - 1 ) {
16
+ return path;
17
+ }
18
+
19
+ return ntPathString.rfind (L" \\\\ " , 0 ) == 0
20
+ ? ntPathString.replace (0 , 2 , L" \\\\ ?\\ UNC\\ " )
21
+ : ntPathString.replace (0 , 0 , L" \\\\ ?\\ " );
22
+ }
23
+
3
24
static std::wstring convertMultiByteToWideChar (const std::string &multiByte) {
4
25
const int wlen = MultiByteToWideChar (CP_UTF8, 0 , multiByte.data (), -1 , 0 , 0 );
5
26
@@ -8,11 +29,13 @@ static std::wstring convertMultiByteToWideChar(const std::string &multiByte) {
8
29
}
9
30
10
31
std::wstring wideString;
11
- wideString.resize (wlen-1 );
32
+ wideString.resize (wlen - 1 );
33
+
12
34
int failureToResolveUTF8 = MultiByteToWideChar (CP_UTF8, 0 , multiByte.data (), -1 , &(wideString[0 ]), wlen);
13
35
if (failureToResolveUTF8 == 0 ) {
14
36
return std::wstring ();
15
37
}
38
+
16
39
return wideString;
17
40
}
18
41
@@ -35,13 +58,18 @@ Controller::Controller(std::shared_ptr<EventQueue> queue, const std::string &pat
35
58
: mDirectoryHandle(INVALID_HANDLE_VALUE)
36
59
{
37
60
auto widePath = convertMultiByteToWideChar (path);
61
+ const bool isNt = isNtPath (widePath);
62
+ if (!isNt) {
63
+ // We convert to an NT Path to support paths > MAX_PATH
64
+ widePath = prefixWithNtPath (widePath);
65
+ }
38
66
mDirectoryHandle = openDirectory (widePath);
39
67
40
68
if (mDirectoryHandle == INVALID_HANDLE_VALUE) {
41
69
return ;
42
70
}
43
71
44
- mWatcher .reset (new Watcher (queue, mDirectoryHandle , widePath));
72
+ mWatcher .reset (new Watcher (queue, mDirectoryHandle , widePath, isNt ));
45
73
}
46
74
47
75
Controller::~Controller () {
@@ -63,5 +91,5 @@ bool Controller::hasErrored() {
63
91
}
64
92
65
93
bool Controller::isWatching () {
66
- return mWatcher ->isRunning ();
94
+ return ! hasErrored () && mWatcher ->isRunning ();
67
95
}
0 commit comments