Use OsStr for path on both Windows and non-Windows systems
This commit is contained in:
parent
24bd6735bc
commit
7d928a3221
@ -6,14 +6,35 @@
|
|||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
|
|
||||||
#if defined(_WIN32) || defined(_WIN64)
|
#if defined(_WIN32)
|
||||||
#include <direct.h>
|
#include <direct.h>
|
||||||
#include "../windows/realpath.c"
|
|
||||||
#include "../windows/utf16.c"
|
#include "../windows/utf16.c"
|
||||||
// use wide char functions for unicode support / longer paths (potentially)
|
// use wide char functions for unicode support / longer paths (potentially)
|
||||||
// opendir() is provided by mingw and does unicode convertion already
|
#include "../windows/realpath.c"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if !defined(_WIN32)
|
||||||
|
typedef char* OsStr;
|
||||||
|
#define OS_C(C) C
|
||||||
|
#define toOsStr toCStr
|
||||||
|
#define freeOsStr freeCStr
|
||||||
|
#define OsStrDecode0 utf8Decode0
|
||||||
|
#else
|
||||||
|
typedef WCHAR* OsStr;
|
||||||
|
#define OS_C(C) L##C
|
||||||
|
#define toOsStr toWStr
|
||||||
|
#define freeOsStr freeWStr
|
||||||
|
#define OsStrDecode0 utf16Decode0
|
||||||
|
#define DIR _WDIR
|
||||||
|
#define dirent _wdirent
|
||||||
|
#define opendir _wopendir
|
||||||
|
#define readdir _wreaddir
|
||||||
|
#define closedir _wclosedir
|
||||||
|
#define mkdir(P, IGNORE) _wmkdir(P)
|
||||||
|
#define access _waccess
|
||||||
|
#define rename _wrename
|
||||||
|
#define unlink _wunlink
|
||||||
|
#endif
|
||||||
|
|
||||||
FILE* file_open(B path, char* desc, char* mode) { // doesn't consume
|
FILE* file_open(B path, char* desc, char* mode) { // doesn't consume
|
||||||
#if !defined(_WIN32)
|
#if !defined(_WIN32)
|
||||||
@ -33,12 +54,9 @@ FILE* file_open(B path, char* desc, char* mode) { // doesn't consume
|
|||||||
return f;
|
return f;
|
||||||
}
|
}
|
||||||
static DIR* dir_open(B path) { // doesn't consume
|
static DIR* dir_open(B path) { // doesn't consume
|
||||||
u64 plen = utf8lenB(path);
|
OsStr p = toOsStr(path);
|
||||||
TALLOC(char, p, plen+1);
|
|
||||||
toUTF8(path, p);
|
|
||||||
p[plen] = 0;
|
|
||||||
DIR* f = opendir(p);
|
DIR* f = opendir(p);
|
||||||
TFREE(p);
|
freeOsStr(p);
|
||||||
if (f==NULL) thrF("Couldn't open directory \"%R\"", path);
|
if (f==NULL) thrF("Couldn't open directory \"%R\"", path);
|
||||||
return f;
|
return f;
|
||||||
}
|
}
|
||||||
@ -184,16 +202,13 @@ B path_abs(B path) {
|
|||||||
return path; // lazy
|
return path; // lazy
|
||||||
#else
|
#else
|
||||||
if (q_N(path)) return path;
|
if (q_N(path)) return path;
|
||||||
u64 plen = utf8lenB(path);
|
OsStr p = toOsStr(path);
|
||||||
TALLOC(char, p, plen+1);
|
OsStr res = realpath(p, NULL);
|
||||||
toUTF8(path, p);
|
|
||||||
p[plen] = 0;
|
|
||||||
char* res = realpath(p, NULL);
|
|
||||||
if (res==NULL) thrF("Failed to resolve \"%R\": %S", path, strerror(errno));
|
if (res==NULL) thrF("Failed to resolve \"%R\": %S", path, strerror(errno));
|
||||||
B r = utf8Decode0(res);
|
B r = OsStrDecode0(res);
|
||||||
free(res);
|
free(res);
|
||||||
dec(path);
|
dec(path);
|
||||||
TFREE(p);
|
freeOsStr(p);
|
||||||
return r;
|
return r;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
@ -264,8 +279,10 @@ B path_list(B path) {
|
|||||||
struct dirent *c;
|
struct dirent *c;
|
||||||
B res = emptySVec();
|
B res = emptySVec();
|
||||||
while ((c = readdir(d)) != NULL) {
|
while ((c = readdir(d)) != NULL) {
|
||||||
char* name = c->d_name;
|
OsStr name = c->d_name;
|
||||||
if (name[0]=='.'? !(name[1]==0 || (name[1]=='.'&&name[2]==0)) : true) res = vec_addN(res, utf8Decode(name, strlen(name)));
|
if (name[0]==OS_C('.')? !(name[1]==0 || (name[1]==OS_C('.')&&name[2]==0)) : true) {
|
||||||
|
res = vec_addN(res, OsStrDecode0(name));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
closedir(d);
|
closedir(d);
|
||||||
dec(path);
|
dec(path);
|
||||||
@ -393,61 +410,39 @@ void mmap_init() { }
|
|||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
|
|
||||||
bool dir_create(B path) {
|
bool dir_create(B path) {
|
||||||
#if !defined(_WIN32)
|
OsStr p = toOsStr(path);
|
||||||
char* p = toCStr(path);
|
|
||||||
bool r = mkdir(p, S_IRWXU) == 0;
|
bool r = mkdir(p, S_IRWXU) == 0;
|
||||||
freeCStr(p);
|
freeOsStr(p);
|
||||||
#else
|
|
||||||
WCHAR* p = toWStr(path);
|
|
||||||
bool r = _wmkdir(p) == 0;
|
|
||||||
freeWStr(p);
|
|
||||||
#endif
|
|
||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool path_rename(B old_path, B new_path) {
|
bool path_rename(B old_path, B new_path) {
|
||||||
#if !defined(_WIN32)
|
OsStr old = toOsStr(old_path);
|
||||||
char* old = toCStr(old_path);
|
OsStr new = toOsStr(new_path);
|
||||||
char* new = toCStr(new_path);
|
|
||||||
// TODO Fix race condition, e.g., with renameat2 on Linux, etc.
|
// TODO Fix race condition, e.g., with renameat2 on Linux, etc.
|
||||||
bool ok = access(new, F_OK) != 0 && rename(old, new) == 0;
|
bool ok = access(new, F_OK) != 0 && rename(old, new) == 0;
|
||||||
freeCStr(new);
|
freeOsStr(new);
|
||||||
freeCStr(old);
|
freeOsStr(old);
|
||||||
#else
|
|
||||||
WCHAR* old = toWStr(old_path);
|
|
||||||
WCHAR* new = toWStr(new_path);
|
|
||||||
bool ok = _waccess(new, F_OK) != 0 && _wrename(old, new) == 0;
|
|
||||||
freeWStr(new);
|
|
||||||
freeWStr(old);
|
|
||||||
#endif
|
|
||||||
dec(old_path);
|
dec(old_path);
|
||||||
return ok;
|
return ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool path_remove(B path) {
|
bool path_remove(B path) {
|
||||||
#if !defined(_WIN32)
|
OsStr p = toOsStr(path);
|
||||||
char* p = toCStr(path);
|
|
||||||
bool ok = unlink(p) == 0;
|
bool ok = unlink(p) == 0;
|
||||||
freeCStr(p);
|
freeOsStr(p);
|
||||||
#else
|
|
||||||
WCHAR* p = toWStr(path);
|
|
||||||
bool ok = _wunlink(p) == 0;
|
|
||||||
freeWStr(p);
|
|
||||||
#endif
|
|
||||||
dec(path);
|
dec(path);
|
||||||
return ok;
|
return ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
int path_stat(struct stat* s, B path) { // doesn't consume; get stat of s; errors if path isn't string; returns non-zero on failure
|
int path_stat(struct stat* s, B path) { // doesn't consume; get stat of s; errors if path isn't string; returns non-zero on failure
|
||||||
|
OsStr p = toOsStr(path);
|
||||||
#if !defined(_WIN32)
|
#if !defined(_WIN32)
|
||||||
char* p = toCStr(path);
|
|
||||||
int r = stat(p, s);
|
int r = stat(p, s);
|
||||||
freeCStr(p);
|
|
||||||
#else
|
#else
|
||||||
WCHAR* p = toWStr(path);
|
|
||||||
int r = wstat(p, s);
|
int r = wstat(p, s);
|
||||||
freeWStr(p);
|
|
||||||
#endif
|
#endif
|
||||||
|
freeOsStr(p);
|
||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -64,6 +64,10 @@ static B utf16Decode(const WCHAR* s, i64 len) {
|
|||||||
#undef UTF16_SURROGATE
|
#undef UTF16_SURROGATE
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static B utf16Decode0(const WCHAR* s) {
|
||||||
|
return utf16Decode(s, wcslen(s));
|
||||||
|
}
|
||||||
|
|
||||||
static WCHAR* toWStr(B x) { // doesn't consume
|
static WCHAR* toWStr(B x) { // doesn't consume
|
||||||
u64 len = utf16lenB(x);
|
u64 len = utf16lenB(x);
|
||||||
TALLOC(WCHAR, p, len+1);
|
TALLOC(WCHAR, p, len+1);
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user