|
|
|
@ -207,6 +207,60 @@ static inline time_t FileTimeToUnixTime(const FILETIME FileTime) |
|
|
|
return (time_t)UnixTime; |
|
|
|
} |
|
|
|
|
|
|
|
CWD_API int php_sys_readlink(const char *link, char *target, size_t target_len){ /* {{{ */ |
|
|
|
HINSTANCE kernel32; |
|
|
|
HANDLE hFile; |
|
|
|
DWORD dwRet; |
|
|
|
|
|
|
|
typedef BOOL (WINAPI *gfpnh_func)(HANDLE, LPTSTR, DWORD, DWORD); |
|
|
|
gfpnh_func pGetFinalPathNameByHandle; |
|
|
|
|
|
|
|
kernel32 = LoadLibrary("kernel32.dll"); |
|
|
|
|
|
|
|
if (kernel32) { |
|
|
|
pGetFinalPathNameByHandle = (gfpnh_func)GetProcAddress(kernel32, "GetFinalPathNameByHandleA"); |
|
|
|
if (pGetFinalPathNameByHandle == NULL) { |
|
|
|
return -1; |
|
|
|
} |
|
|
|
} else { |
|
|
|
return -1; |
|
|
|
} |
|
|
|
|
|
|
|
hFile = CreateFile(link, // file to open |
|
|
|
GENERIC_READ, // open for reading |
|
|
|
FILE_SHARE_READ, // share for reading |
|
|
|
NULL, // default security |
|
|
|
OPEN_EXISTING, // existing file only |
|
|
|
FILE_FLAG_BACKUP_SEMANTICS, // normal file |
|
|
|
NULL); // no attr. template |
|
|
|
|
|
|
|
if( hFile == INVALID_HANDLE_VALUE) { |
|
|
|
return -1; |
|
|
|
} |
|
|
|
|
|
|
|
dwRet = pGetFinalPathNameByHandle(hFile, target, MAXPATHLEN, VOLUME_NAME_DOS); |
|
|
|
if(dwRet >= MAXPATHLEN) { |
|
|
|
return -1; |
|
|
|
} |
|
|
|
|
|
|
|
CloseHandle(hFile); |
|
|
|
|
|
|
|
if(dwRet > 4) { |
|
|
|
/* Skip first 4 characters if they are "\??\" */ |
|
|
|
if(target[0] == '\\' && target[1] == '\\' && target[2] == '?' && target[3] == '\\') { |
|
|
|
char tmp[MAXPATHLEN]; |
|
|
|
|
|
|
|
dwRet -= 4; |
|
|
|
memcpy(tmp, target + 4, dwRet); |
|
|
|
memcpy(target, tmp, dwRet); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
target[dwRet] = '\0'; |
|
|
|
return dwRet; |
|
|
|
} |
|
|
|
/* }}} */ |
|
|
|
|
|
|
|
CWD_API int php_sys_stat_ex(const char *path, struct stat *buf, int lstat) /* {{{ */ |
|
|
|
{ |
|
|
|
WIN32_FILE_ATTRIBUTE_DATA data; |
|
|
|
@ -756,7 +810,7 @@ static int tsrm_realpath_r(char *path, int start, int len, int *ll, time_t *t, i |
|
|
|
tmp = tsrm_do_alloca(len+1, use_heap); |
|
|
|
memcpy(tmp, path, len+1); |
|
|
|
|
|
|
|
if(save && |
|
|
|
if(save && |
|
|
|
!(IS_UNC_PATH(path, len) && len >= 3 && path[2] != '?') && |
|
|
|
(data.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)) { |
|
|
|
/* File is a reparse point. Get the target */ |
|
|
|
|