-
Notifications
You must be signed in to change notification settings - Fork 65
/
sqWin32File.h
49 lines (41 loc) · 2.04 KB
/
sqWin32File.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
#ifndef __SQ_WIN32_FILE_H
#define __SQ_WIN32_FILE_H
/**
Converts multi-byte characters to wide characters. Handles paths longer
than 260 characters (including NULL) by prepending "\\?\" to encode UNC
paths as suggested in http://msdn.microsoft.com/en-us/library/windows/
desktop/aa365247%28v=vs.85%29.aspx#maxpath
"The maximum path of 32,767 characters is approximate,
because the "\\?\" prefix may be expanded to a longer
string by the system at run time, and this expansion
applies to the total length."
Note that we do not check for the correct path component size,
which should be MAX_PATH in general but can vary between file systems.
Actually, we should perform an additional check with
GetVolumneInformation to acquire lpMaximumComponentLength.
Note that another possibility would be to use 8.3 aliases
for path components like the Windows Explorer does. However,
this feature also depends on the volume specifications.
Calling alloca() should be fine because we limit path length to 32k.
Stack size limit is much higher.
When using an API to create a directory, the specified path cannot be
so long that you cannot append an 8.3 file name (that is, the directory
name cannot exceed MAX_PATH minus 12).
**/
#include <malloc.h>
#define ALLOC_WIN32_PATH(out_path, in_name, in_size) { \
int sz = MultiByteToWideChar(CP_UTF8, 0, in_name, in_size, NULL, 0); \
if(sz >= 32767) FAIL(); \
if(sz >= MAX_PATH-12 /* for directory creation; see above */) { \
out_path = (WCHAR*)alloca((sz + 4 + 1) * sizeof(WCHAR)); \
out_path[0] = L'\\'; out_path[1] = L'\\'; \
out_path[2] = L'?'; out_path[3] = L'\\'; \
MultiByteToWideChar(CP_UTF8, 0, in_name, in_size, out_path + 4, sz); \
out_path[sz + 4] = 0; \
} else { \
out_path = (WCHAR*)alloca((sz + 1) * sizeof(WCHAR)); \
MultiByteToWideChar(CP_UTF8, 0, in_name, in_size, out_path, sz); \
out_path[sz] = 0; \
} \
}
#endif /* __SQ_WIN32_FILE_H */