Mercurial > vba-clojure
diff src/win32/7zip/7z/CPP/Windows/FileDir.cpp @ 1:f9f4f1b99eed
importing src directory
author | Robert McIntyre <rlm@mit.edu> |
---|---|
date | Sat, 03 Mar 2012 10:31:27 -0600 |
parents | |
children |
line wrap: on
line diff
1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/src/win32/7zip/7z/CPP/Windows/FileDir.cpp Sat Mar 03 10:31:27 2012 -0600 1.3 @@ -0,0 +1,841 @@ 1.4 +// Windows/FileDir.cpp 1.5 + 1.6 +#include "StdAfx.h" 1.7 + 1.8 +#include "FileDir.h" 1.9 +#include "FileName.h" 1.10 +#include "FileFind.h" 1.11 +#include "Defs.h" 1.12 +#ifndef _UNICODE 1.13 +#include "../Common/StringConvert.h" 1.14 +#endif 1.15 + 1.16 +#ifndef _UNICODE 1.17 +extern bool g_IsNT; 1.18 +#endif 1.19 + 1.20 +namespace NWindows { 1.21 +namespace NFile { 1.22 + 1.23 +#if defined(WIN_LONG_PATH) && defined(_UNICODE) 1.24 +#define WIN_LONG_PATH2 1.25 +#endif 1.26 + 1.27 +// SetCurrentDirectory doesn't support \\?\ prefix 1.28 + 1.29 +#ifdef WIN_LONG_PATH 1.30 +bool GetLongPathBase(LPCWSTR fileName, UString &res); 1.31 +bool GetLongPath(LPCWSTR fileName, UString &res); 1.32 +#endif 1.33 + 1.34 +namespace NDirectory { 1.35 + 1.36 +#ifndef _UNICODE 1.37 +static inline UINT GetCurrentCodePage() { return ::AreFileApisANSI() ? CP_ACP : CP_OEMCP; } 1.38 +static UString GetUnicodePath(const CSysString &sysPath) 1.39 + { return MultiByteToUnicodeString(sysPath, GetCurrentCodePage()); } 1.40 +static CSysString GetSysPath(LPCWSTR sysPath) 1.41 + { return UnicodeStringToMultiByte(sysPath, GetCurrentCodePage()); } 1.42 +#endif 1.43 + 1.44 +bool MyGetWindowsDirectory(CSysString &path) 1.45 +{ 1.46 + UINT needLength = ::GetWindowsDirectory(path.GetBuffer(MAX_PATH + 1), MAX_PATH + 1); 1.47 + path.ReleaseBuffer(); 1.48 + return (needLength > 0 && needLength <= MAX_PATH); 1.49 +} 1.50 + 1.51 +bool MyGetSystemDirectory(CSysString &path) 1.52 +{ 1.53 + UINT needLength = ::GetSystemDirectory(path.GetBuffer(MAX_PATH + 1), MAX_PATH + 1); 1.54 + path.ReleaseBuffer(); 1.55 + return (needLength > 0 && needLength <= MAX_PATH); 1.56 +} 1.57 + 1.58 +#ifndef _UNICODE 1.59 +bool MyGetWindowsDirectory(UString &path) 1.60 +{ 1.61 + if (g_IsNT) 1.62 + { 1.63 + UINT needLength = ::GetWindowsDirectoryW(path.GetBuffer(MAX_PATH + 1), MAX_PATH + 1); 1.64 + path.ReleaseBuffer(); 1.65 + return (needLength > 0 && needLength <= MAX_PATH); 1.66 + } 1.67 + CSysString sysPath; 1.68 + if (!MyGetWindowsDirectory(sysPath)) 1.69 + return false; 1.70 + path = GetUnicodePath(sysPath); 1.71 + return true; 1.72 +} 1.73 + 1.74 +bool MyGetSystemDirectory(UString &path) 1.75 +{ 1.76 + if (g_IsNT) 1.77 + { 1.78 + UINT needLength = ::GetSystemDirectoryW(path.GetBuffer(MAX_PATH + 1), MAX_PATH + 1); 1.79 + path.ReleaseBuffer(); 1.80 + return (needLength > 0 && needLength <= MAX_PATH); 1.81 + } 1.82 + CSysString sysPath; 1.83 + if (!MyGetSystemDirectory(sysPath)) 1.84 + return false; 1.85 + path = GetUnicodePath(sysPath); 1.86 + return true; 1.87 +} 1.88 +#endif 1.89 + 1.90 +bool SetDirTime(LPCWSTR fileName, const FILETIME *cTime, const FILETIME *aTime, const FILETIME *mTime) 1.91 +{ 1.92 + #ifndef _UNICODE 1.93 + if (!g_IsNT) 1.94 + { 1.95 + ::SetLastError(ERROR_CALL_NOT_IMPLEMENTED); 1.96 + return false; 1.97 + } 1.98 + #endif 1.99 + HANDLE hDir = ::CreateFileW(fileName, GENERIC_WRITE, 1.100 + FILE_SHARE_READ | FILE_SHARE_WRITE, 1.101 + NULL, OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS, NULL); 1.102 + #ifdef WIN_LONG_PATH 1.103 + if (hDir == INVALID_HANDLE_VALUE) 1.104 + { 1.105 + UString longPath; 1.106 + if (GetLongPath(fileName, longPath)) 1.107 + hDir = ::CreateFileW(longPath, GENERIC_WRITE, 1.108 + FILE_SHARE_READ | FILE_SHARE_WRITE, 1.109 + NULL, OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS, NULL); 1.110 + } 1.111 + #endif 1.112 + 1.113 + bool res = false; 1.114 + if (hDir != INVALID_HANDLE_VALUE) 1.115 + { 1.116 + res = BOOLToBool(::SetFileTime(hDir, cTime, aTime, mTime)); 1.117 + ::CloseHandle(hDir); 1.118 + } 1.119 + return res; 1.120 +} 1.121 + 1.122 +bool MySetFileAttributes(LPCTSTR fileName, DWORD fileAttributes) 1.123 +{ 1.124 + if (::SetFileAttributes(fileName, fileAttributes)) 1.125 + return true; 1.126 + #ifdef WIN_LONG_PATH2 1.127 + UString longPath; 1.128 + if (GetLongPath(fileName, longPath)) 1.129 + return BOOLToBool(::SetFileAttributesW(longPath, fileAttributes)); 1.130 + #endif 1.131 + return false; 1.132 +} 1.133 + 1.134 +bool MyRemoveDirectory(LPCTSTR pathName) 1.135 +{ 1.136 + if (::RemoveDirectory(pathName)) 1.137 + return true; 1.138 + #ifdef WIN_LONG_PATH2 1.139 + UString longPath; 1.140 + if (GetLongPath(pathName, longPath)) 1.141 + return BOOLToBool(::RemoveDirectoryW(longPath)); 1.142 + #endif 1.143 + return false; 1.144 +} 1.145 + 1.146 +#ifdef WIN_LONG_PATH 1.147 +bool GetLongPaths(LPCWSTR s1, LPCWSTR s2, UString &d1, UString &d2) 1.148 +{ 1.149 + if (!GetLongPathBase(s1, d1) || !GetLongPathBase(s2, d2)) 1.150 + return false; 1.151 + if (d1.IsEmpty() && d2.IsEmpty()) return false; 1.152 + if (d1.IsEmpty()) d1 = s1; 1.153 + if (d2.IsEmpty()) d2 = s2; 1.154 + return true; 1.155 +} 1.156 +#endif 1.157 + 1.158 +bool MyMoveFile(LPCTSTR existFileName, LPCTSTR newFileName) 1.159 +{ 1.160 + if (::MoveFile(existFileName, newFileName)) 1.161 + return true; 1.162 + #ifdef WIN_LONG_PATH2 1.163 + UString d1, d2; 1.164 + if (GetLongPaths(existFileName, newFileName, d1, d2)) 1.165 + return BOOLToBool(::MoveFileW(d1, d2)); 1.166 + #endif 1.167 + return false; 1.168 +} 1.169 + 1.170 +#ifndef _UNICODE 1.171 +bool MySetFileAttributes(LPCWSTR fileName, DWORD fileAttributes) 1.172 +{ 1.173 + if (!g_IsNT) 1.174 + return MySetFileAttributes(GetSysPath(fileName), fileAttributes); 1.175 + if (::SetFileAttributesW(fileName, fileAttributes)) 1.176 + return true; 1.177 + #ifdef WIN_LONG_PATH 1.178 + UString longPath; 1.179 + if (GetLongPath(fileName, longPath)) 1.180 + return BOOLToBool(::SetFileAttributesW(longPath, fileAttributes)); 1.181 + #endif 1.182 + return false; 1.183 +} 1.184 + 1.185 + 1.186 +bool MyRemoveDirectory(LPCWSTR pathName) 1.187 +{ 1.188 + if (!g_IsNT) 1.189 + return MyRemoveDirectory(GetSysPath(pathName)); 1.190 + if (::RemoveDirectoryW(pathName)) 1.191 + return true; 1.192 + #ifdef WIN_LONG_PATH 1.193 + UString longPath; 1.194 + if (GetLongPath(pathName, longPath)) 1.195 + return BOOLToBool(::RemoveDirectoryW(longPath)); 1.196 + #endif 1.197 + return false; 1.198 +} 1.199 + 1.200 +bool MyMoveFile(LPCWSTR existFileName, LPCWSTR newFileName) 1.201 +{ 1.202 + if (!g_IsNT) 1.203 + return MyMoveFile(GetSysPath(existFileName), GetSysPath(newFileName)); 1.204 + if (::MoveFileW(existFileName, newFileName)) 1.205 + return true; 1.206 + #ifdef WIN_LONG_PATH 1.207 + UString d1, d2; 1.208 + if (GetLongPaths(existFileName, newFileName, d1, d2)) 1.209 + return BOOLToBool(::MoveFileW(d1, d2)); 1.210 + #endif 1.211 + return false; 1.212 +} 1.213 +#endif 1.214 + 1.215 +bool MyCreateDirectory(LPCTSTR pathName) 1.216 +{ 1.217 + if (::CreateDirectory(pathName, NULL)) 1.218 + return true; 1.219 + #ifdef WIN_LONG_PATH2 1.220 + if (::GetLastError() != ERROR_ALREADY_EXISTS) 1.221 + { 1.222 + UString longPath; 1.223 + if (GetLongPath(pathName, longPath)) 1.224 + return BOOLToBool(::CreateDirectoryW(longPath, NULL)); 1.225 + } 1.226 + #endif 1.227 + return false; 1.228 +} 1.229 + 1.230 +#ifndef _UNICODE 1.231 +bool MyCreateDirectory(LPCWSTR pathName) 1.232 +{ 1.233 + if (!g_IsNT) 1.234 + return MyCreateDirectory(GetSysPath(pathName)); 1.235 + if (::CreateDirectoryW(pathName, NULL)) 1.236 + return true; 1.237 + #ifdef WIN_LONG_PATH 1.238 + if (::GetLastError() != ERROR_ALREADY_EXISTS) 1.239 + { 1.240 + UString longPath; 1.241 + if (GetLongPath(pathName, longPath)) 1.242 + return BOOLToBool(::CreateDirectoryW(longPath, NULL)); 1.243 + } 1.244 + #endif 1.245 + return false; 1.246 +} 1.247 +#endif 1.248 + 1.249 +/* 1.250 +bool CreateComplexDirectory(LPCTSTR pathName) 1.251 +{ 1.252 + NName::CParsedPath path; 1.253 + path.ParsePath(pathName); 1.254 + CSysString fullPath = path.Prefix; 1.255 + DWORD errorCode = ERROR_SUCCESS; 1.256 + for (int i = 0; i < path.PathParts.Size(); i++) 1.257 + { 1.258 + const CSysString &string = path.PathParts[i]; 1.259 + if (string.IsEmpty()) 1.260 + { 1.261 + if (i != path.PathParts.Size() - 1) 1.262 + return false; 1.263 + return true; 1.264 + } 1.265 + fullPath += path.PathParts[i]; 1.266 + if (!MyCreateDirectory(fullPath)) 1.267 + { 1.268 + DWORD errorCode = GetLastError(); 1.269 + if (errorCode != ERROR_ALREADY_EXISTS) 1.270 + return false; 1.271 + } 1.272 + fullPath += NName::kDirDelimiter; 1.273 + } 1.274 + return true; 1.275 +} 1.276 +*/ 1.277 + 1.278 +bool CreateComplexDirectory(LPCTSTR _aPathName) 1.279 +{ 1.280 + CSysString pathName = _aPathName; 1.281 + int pos = pathName.ReverseFind(TEXT(CHAR_PATH_SEPARATOR)); 1.282 + if (pos > 0 && pos == pathName.Length() - 1) 1.283 + { 1.284 + if (pathName.Length() == 3 && pathName[1] == ':') 1.285 + return true; // Disk folder; 1.286 + pathName.Delete(pos); 1.287 + } 1.288 + CSysString pathName2 = pathName; 1.289 + pos = pathName.Length(); 1.290 + for (;;) 1.291 + { 1.292 + if (MyCreateDirectory(pathName)) 1.293 + break; 1.294 + if (::GetLastError() == ERROR_ALREADY_EXISTS) 1.295 + { 1.296 + NFind::CFileInfo fileInfo; 1.297 + if (!NFind::FindFile(pathName, fileInfo)) // For network folders 1.298 + return true; 1.299 + if (!fileInfo.IsDir()) 1.300 + return false; 1.301 + break; 1.302 + } 1.303 + pos = pathName.ReverseFind(TEXT(CHAR_PATH_SEPARATOR)); 1.304 + if (pos < 0 || pos == 0) 1.305 + return false; 1.306 + if (pathName[pos - 1] == ':') 1.307 + return false; 1.308 + pathName = pathName.Left(pos); 1.309 + } 1.310 + pathName = pathName2; 1.311 + while (pos < pathName.Length()) 1.312 + { 1.313 + pos = pathName.Find(TEXT(CHAR_PATH_SEPARATOR), pos + 1); 1.314 + if (pos < 0) 1.315 + pos = pathName.Length(); 1.316 + if (!MyCreateDirectory(pathName.Left(pos))) 1.317 + return false; 1.318 + } 1.319 + return true; 1.320 +} 1.321 + 1.322 +#ifndef _UNICODE 1.323 + 1.324 +bool CreateComplexDirectory(LPCWSTR _aPathName) 1.325 +{ 1.326 + UString pathName = _aPathName; 1.327 + int pos = pathName.ReverseFind(WCHAR_PATH_SEPARATOR); 1.328 + if (pos > 0 && pos == pathName.Length() - 1) 1.329 + { 1.330 + if (pathName.Length() == 3 && pathName[1] == L':') 1.331 + return true; // Disk folder; 1.332 + pathName.Delete(pos); 1.333 + } 1.334 + UString pathName2 = pathName; 1.335 + pos = pathName.Length(); 1.336 + for (;;) 1.337 + { 1.338 + if (MyCreateDirectory(pathName)) 1.339 + break; 1.340 + if (::GetLastError() == ERROR_ALREADY_EXISTS) 1.341 + { 1.342 + NFind::CFileInfoW fileInfo; 1.343 + if (!NFind::FindFile(pathName, fileInfo)) // For network folders 1.344 + return true; 1.345 + if (!fileInfo.IsDir()) 1.346 + return false; 1.347 + break; 1.348 + } 1.349 + pos = pathName.ReverseFind(WCHAR_PATH_SEPARATOR); 1.350 + if (pos < 0 || pos == 0) 1.351 + return false; 1.352 + if (pathName[pos - 1] == L':') 1.353 + return false; 1.354 + pathName = pathName.Left(pos); 1.355 + } 1.356 + pathName = pathName2; 1.357 + while (pos < pathName.Length()) 1.358 + { 1.359 + pos = pathName.Find(WCHAR_PATH_SEPARATOR, pos + 1); 1.360 + if (pos < 0) 1.361 + pos = pathName.Length(); 1.362 + if (!MyCreateDirectory(pathName.Left(pos))) 1.363 + return false; 1.364 + } 1.365 + return true; 1.366 +} 1.367 + 1.368 +#endif 1.369 + 1.370 +bool DeleteFileAlways(LPCTSTR name) 1.371 +{ 1.372 + if (!MySetFileAttributes(name, 0)) 1.373 + return false; 1.374 + if (::DeleteFile(name)) 1.375 + return true; 1.376 + #ifdef WIN_LONG_PATH2 1.377 + UString longPath; 1.378 + if (GetLongPath(name, longPath)) 1.379 + return BOOLToBool(::DeleteFileW(longPath)); 1.380 + #endif 1.381 + return false; 1.382 +} 1.383 + 1.384 +#ifndef _UNICODE 1.385 +bool DeleteFileAlways(LPCWSTR name) 1.386 +{ 1.387 + if (!g_IsNT) 1.388 + return DeleteFileAlways(GetSysPath(name)); 1.389 + if (!MySetFileAttributes(name, 0)) 1.390 + return false; 1.391 + if (::DeleteFileW(name)) 1.392 + return true; 1.393 + #ifdef WIN_LONG_PATH 1.394 + UString longPath; 1.395 + if (GetLongPath(name, longPath)) 1.396 + return BOOLToBool(::DeleteFileW(longPath)); 1.397 + #endif 1.398 + return false; 1.399 +} 1.400 +#endif 1.401 + 1.402 +static bool RemoveDirectorySubItems2(const CSysString pathPrefix, const NFind::CFileInfo &fileInfo) 1.403 +{ 1.404 + if (fileInfo.IsDir()) 1.405 + return RemoveDirectoryWithSubItems(pathPrefix + fileInfo.Name); 1.406 + return DeleteFileAlways(pathPrefix + fileInfo.Name); 1.407 +} 1.408 + 1.409 +bool RemoveDirectoryWithSubItems(const CSysString &path) 1.410 +{ 1.411 + NFind::CFileInfo fileInfo; 1.412 + CSysString pathPrefix = path + NName::kDirDelimiter; 1.413 + { 1.414 + NFind::CEnumerator enumerator(pathPrefix + TCHAR(NName::kAnyStringWildcard)); 1.415 + while (enumerator.Next(fileInfo)) 1.416 + if (!RemoveDirectorySubItems2(pathPrefix, fileInfo)) 1.417 + return false; 1.418 + } 1.419 + if (!MySetFileAttributes(path, 0)) 1.420 + return false; 1.421 + return MyRemoveDirectory(path); 1.422 +} 1.423 + 1.424 +#ifndef _UNICODE 1.425 +static bool RemoveDirectorySubItems2(const UString pathPrefix, const NFind::CFileInfoW &fileInfo) 1.426 +{ 1.427 + if (fileInfo.IsDir()) 1.428 + return RemoveDirectoryWithSubItems(pathPrefix + fileInfo.Name); 1.429 + return DeleteFileAlways(pathPrefix + fileInfo.Name); 1.430 +} 1.431 +bool RemoveDirectoryWithSubItems(const UString &path) 1.432 +{ 1.433 + NFind::CFileInfoW fileInfo; 1.434 + UString pathPrefix = path + UString(NName::kDirDelimiter); 1.435 + { 1.436 + NFind::CEnumeratorW enumerator(pathPrefix + UString(NName::kAnyStringWildcard)); 1.437 + while (enumerator.Next(fileInfo)) 1.438 + if (!RemoveDirectorySubItems2(pathPrefix, fileInfo)) 1.439 + return false; 1.440 + } 1.441 + if (!MySetFileAttributes(path, 0)) 1.442 + return false; 1.443 + return MyRemoveDirectory(path); 1.444 +} 1.445 +#endif 1.446 + 1.447 +#ifndef _WIN32_WCE 1.448 + 1.449 +bool MyGetShortPathName(LPCTSTR longPath, CSysString &shortPath) 1.450 +{ 1.451 + DWORD needLength = ::GetShortPathName(longPath, shortPath.GetBuffer(MAX_PATH + 1), MAX_PATH + 1); 1.452 + shortPath.ReleaseBuffer(); 1.453 + return (needLength > 0 && needLength < MAX_PATH); 1.454 +} 1.455 + 1.456 +bool MyGetFullPathName(LPCTSTR fileName, CSysString &resultPath, int &fileNamePartStartIndex) 1.457 +{ 1.458 + resultPath.Empty(); 1.459 + LPTSTR fileNamePointer = 0; 1.460 + LPTSTR buffer = resultPath.GetBuffer(MAX_PATH); 1.461 + DWORD needLength = ::GetFullPathName(fileName, MAX_PATH + 1, buffer, &fileNamePointer); 1.462 + resultPath.ReleaseBuffer(); 1.463 + if (needLength == 0) 1.464 + return false; 1.465 + if (needLength >= MAX_PATH) 1.466 + { 1.467 + #ifdef WIN_LONG_PATH2 1.468 + needLength++; 1.469 + buffer = resultPath.GetBuffer(needLength + 1); 1.470 + DWORD needLength2 = ::GetFullPathNameW(fileName, needLength, buffer, &fileNamePointer); 1.471 + resultPath.ReleaseBuffer(); 1.472 + if (needLength2 == 0 || needLength2 > needLength) 1.473 + #endif 1.474 + return false; 1.475 + } 1.476 + if (fileNamePointer == 0) 1.477 + fileNamePartStartIndex = lstrlen(fileName); 1.478 + else 1.479 + fileNamePartStartIndex = (int)(fileNamePointer - buffer); 1.480 + return true; 1.481 +} 1.482 + 1.483 +#ifndef _UNICODE 1.484 +bool MyGetFullPathName(LPCWSTR fileName, UString &resultPath, int &fileNamePartStartIndex) 1.485 +{ 1.486 + resultPath.Empty(); 1.487 + if (g_IsNT) 1.488 + { 1.489 + LPWSTR fileNamePointer = 0; 1.490 + LPWSTR buffer = resultPath.GetBuffer(MAX_PATH); 1.491 + DWORD needLength = ::GetFullPathNameW(fileName, MAX_PATH + 1, buffer, &fileNamePointer); 1.492 + resultPath.ReleaseBuffer(); 1.493 + if (needLength == 0) 1.494 + return false; 1.495 + if (needLength >= MAX_PATH) 1.496 + { 1.497 + #ifdef WIN_LONG_PATH 1.498 + needLength++; 1.499 + buffer = resultPath.GetBuffer(needLength + 1); 1.500 + DWORD needLength2 = ::GetFullPathNameW(fileName, needLength, buffer, &fileNamePointer); 1.501 + resultPath.ReleaseBuffer(); 1.502 + if (needLength2 == 0 || needLength2 > needLength) 1.503 + #endif 1.504 + return false; 1.505 + } 1.506 + if (fileNamePointer == 0) 1.507 + fileNamePartStartIndex = MyStringLen(fileName); 1.508 + else 1.509 + fileNamePartStartIndex = (int)(fileNamePointer - buffer); 1.510 + } 1.511 + else 1.512 + { 1.513 + CSysString sysPath; 1.514 + if (!MyGetFullPathName(GetSysPath(fileName), sysPath, fileNamePartStartIndex)) 1.515 + return false; 1.516 + UString resultPath1 = GetUnicodePath(sysPath.Left(fileNamePartStartIndex)); 1.517 + UString resultPath2 = GetUnicodePath(sysPath.Mid(fileNamePartStartIndex)); 1.518 + fileNamePartStartIndex = resultPath1.Length(); 1.519 + resultPath = resultPath1 + resultPath2; 1.520 + } 1.521 + return true; 1.522 +} 1.523 +#endif 1.524 + 1.525 + 1.526 +bool MyGetFullPathName(LPCTSTR fileName, CSysString &path) 1.527 +{ 1.528 + int index; 1.529 + return MyGetFullPathName(fileName, path, index); 1.530 +} 1.531 + 1.532 +#ifndef _UNICODE 1.533 +bool MyGetFullPathName(LPCWSTR fileName, UString &path) 1.534 +{ 1.535 + int index; 1.536 + return MyGetFullPathName(fileName, path, index); 1.537 +} 1.538 +#endif 1.539 + 1.540 +bool GetOnlyName(LPCTSTR fileName, CSysString &resultName) 1.541 +{ 1.542 + int index; 1.543 + if (!MyGetFullPathName(fileName, resultName, index)) 1.544 + return false; 1.545 + resultName = resultName.Mid(index); 1.546 + return true; 1.547 +} 1.548 + 1.549 +#ifndef _UNICODE 1.550 +bool GetOnlyName(LPCWSTR fileName, UString &resultName) 1.551 +{ 1.552 + int index; 1.553 + if (!MyGetFullPathName(fileName, resultName, index)) 1.554 + return false; 1.555 + resultName = resultName.Mid(index); 1.556 + return true; 1.557 +} 1.558 +#endif 1.559 + 1.560 +bool GetOnlyDirPrefix(LPCTSTR fileName, CSysString &resultName) 1.561 +{ 1.562 + int index; 1.563 + if (!MyGetFullPathName(fileName, resultName, index)) 1.564 + return false; 1.565 + resultName = resultName.Left(index); 1.566 + return true; 1.567 +} 1.568 + 1.569 +#ifndef _UNICODE 1.570 +bool GetOnlyDirPrefix(LPCWSTR fileName, UString &resultName) 1.571 +{ 1.572 + int index; 1.573 + if (!MyGetFullPathName(fileName, resultName, index)) 1.574 + return false; 1.575 + resultName = resultName.Left(index); 1.576 + return true; 1.577 +} 1.578 +#endif 1.579 + 1.580 +bool MyGetCurrentDirectory(CSysString &path) 1.581 +{ 1.582 + DWORD needLength = ::GetCurrentDirectory(MAX_PATH + 1, path.GetBuffer(MAX_PATH + 1)); 1.583 + path.ReleaseBuffer(); 1.584 + return (needLength > 0 && needLength <= MAX_PATH); 1.585 +} 1.586 + 1.587 +#ifndef _UNICODE 1.588 +bool MySetCurrentDirectory(LPCWSTR path) 1.589 +{ 1.590 + if (g_IsNT) 1.591 + return BOOLToBool(::SetCurrentDirectoryW(path)); 1.592 + return MySetCurrentDirectory(GetSysPath(path)); 1.593 +} 1.594 +bool MyGetCurrentDirectory(UString &path) 1.595 +{ 1.596 + if (g_IsNT) 1.597 + { 1.598 + DWORD needLength = ::GetCurrentDirectoryW(MAX_PATH + 1, path.GetBuffer(MAX_PATH + 1)); 1.599 + path.ReleaseBuffer(); 1.600 + return (needLength > 0 && needLength <= MAX_PATH); 1.601 + } 1.602 + CSysString sysPath; 1.603 + if (!MyGetCurrentDirectory(sysPath)) 1.604 + return false; 1.605 + path = GetUnicodePath(sysPath); 1.606 + return true; 1.607 +} 1.608 +#endif 1.609 +#endif 1.610 + 1.611 +bool MySearchPath(LPCTSTR path, LPCTSTR fileName, LPCTSTR extension, 1.612 + CSysString &resultPath, UINT32 &filePart) 1.613 +{ 1.614 + LPTSTR filePartPointer; 1.615 + DWORD value = ::SearchPath(path, fileName, extension, 1.616 + MAX_PATH, resultPath.GetBuffer(MAX_PATH + 1), &filePartPointer); 1.617 + filePart = (UINT32)(filePartPointer - (LPCTSTR)resultPath); 1.618 + resultPath.ReleaseBuffer(); 1.619 + return (value > 0 && value <= MAX_PATH); 1.620 +} 1.621 + 1.622 +#ifndef _UNICODE 1.623 +bool MySearchPath(LPCWSTR path, LPCWSTR fileName, LPCWSTR extension, 1.624 + UString &resultPath, UINT32 &filePart) 1.625 +{ 1.626 + if (g_IsNT) 1.627 + { 1.628 + LPWSTR filePartPointer = 0; 1.629 + DWORD value = ::SearchPathW(path, fileName, extension, 1.630 + MAX_PATH, resultPath.GetBuffer(MAX_PATH + 1), &filePartPointer); 1.631 + filePart = (UINT32)(filePartPointer - (LPCWSTR)resultPath); 1.632 + resultPath.ReleaseBuffer(); 1.633 + return (value > 0 && value <= MAX_PATH); 1.634 + } 1.635 + 1.636 + CSysString sysPath; 1.637 + if (!MySearchPath( 1.638 + path != 0 ? (LPCTSTR)GetSysPath(path): 0, 1.639 + fileName != 0 ? (LPCTSTR)GetSysPath(fileName): 0, 1.640 + extension != 0 ? (LPCTSTR)GetSysPath(extension): 0, 1.641 + sysPath, filePart)) 1.642 + return false; 1.643 + UString resultPath1 = GetUnicodePath(sysPath.Left(filePart)); 1.644 + UString resultPath2 = GetUnicodePath(sysPath.Mid(filePart)); 1.645 + filePart = resultPath1.Length(); 1.646 + resultPath = resultPath1 + resultPath2; 1.647 + return true; 1.648 +} 1.649 +#endif 1.650 + 1.651 +bool MyGetTempPath(CSysString &path) 1.652 +{ 1.653 + DWORD needLength = ::GetTempPath(MAX_PATH + 1, path.GetBuffer(MAX_PATH + 1)); 1.654 + path.ReleaseBuffer(); 1.655 + return (needLength > 0 && needLength <= MAX_PATH); 1.656 +} 1.657 + 1.658 +#ifndef _UNICODE 1.659 +bool MyGetTempPath(UString &path) 1.660 +{ 1.661 + path.Empty(); 1.662 + if (g_IsNT) 1.663 + { 1.664 + DWORD needLength = ::GetTempPathW(MAX_PATH + 1, path.GetBuffer(MAX_PATH + 1)); 1.665 + path.ReleaseBuffer(); 1.666 + return (needLength > 0 && needLength <= MAX_PATH); 1.667 + } 1.668 + CSysString sysPath; 1.669 + if (!MyGetTempPath(sysPath)) 1.670 + return false; 1.671 + path = GetUnicodePath(sysPath); 1.672 + return true; 1.673 +} 1.674 +#endif 1.675 + 1.676 +UINT MyGetTempFileName(LPCTSTR dirPath, LPCTSTR prefix, CSysString &path) 1.677 +{ 1.678 + UINT number = ::GetTempFileName(dirPath, prefix, 0, path.GetBuffer(MAX_PATH + 1)); 1.679 + path.ReleaseBuffer(); 1.680 + return number; 1.681 +} 1.682 + 1.683 +#ifndef _UNICODE 1.684 +UINT MyGetTempFileName(LPCWSTR dirPath, LPCWSTR prefix, UString &path) 1.685 +{ 1.686 + if (g_IsNT) 1.687 + { 1.688 + UINT number = ::GetTempFileNameW(dirPath, prefix, 0, path.GetBuffer(MAX_PATH)); 1.689 + path.ReleaseBuffer(); 1.690 + return number; 1.691 + } 1.692 + CSysString sysPath; 1.693 + UINT number = MyGetTempFileName( 1.694 + dirPath ? (LPCTSTR)GetSysPath(dirPath): 0, 1.695 + prefix ? (LPCTSTR)GetSysPath(prefix): 0, 1.696 + sysPath); 1.697 + path = GetUnicodePath(sysPath); 1.698 + return number; 1.699 +} 1.700 +#endif 1.701 + 1.702 +UINT CTempFile::Create(LPCTSTR dirPath, LPCTSTR prefix, CSysString &resultPath) 1.703 +{ 1.704 + Remove(); 1.705 + UINT number = MyGetTempFileName(dirPath, prefix, resultPath); 1.706 + if (number != 0) 1.707 + { 1.708 + _fileName = resultPath; 1.709 + _mustBeDeleted = true; 1.710 + } 1.711 + return number; 1.712 +} 1.713 + 1.714 +bool CTempFile::Create(LPCTSTR prefix, CSysString &resultPath) 1.715 +{ 1.716 + CSysString tempPath; 1.717 + if (!MyGetTempPath(tempPath)) 1.718 + return false; 1.719 + if (Create(tempPath, prefix, resultPath) != 0) 1.720 + return true; 1.721 + if (!MyGetWindowsDirectory(tempPath)) 1.722 + return false; 1.723 + return (Create(tempPath, prefix, resultPath) != 0); 1.724 +} 1.725 + 1.726 +bool CTempFile::Remove() 1.727 +{ 1.728 + if (!_mustBeDeleted) 1.729 + return true; 1.730 + _mustBeDeleted = !DeleteFileAlways(_fileName); 1.731 + return !_mustBeDeleted; 1.732 +} 1.733 + 1.734 +#ifndef _UNICODE 1.735 + 1.736 +UINT CTempFileW::Create(LPCWSTR dirPath, LPCWSTR prefix, UString &resultPath) 1.737 +{ 1.738 + Remove(); 1.739 + UINT number = MyGetTempFileName(dirPath, prefix, resultPath); 1.740 + if (number != 0) 1.741 + { 1.742 + _fileName = resultPath; 1.743 + _mustBeDeleted = true; 1.744 + } 1.745 + return number; 1.746 +} 1.747 + 1.748 +bool CTempFileW::Create(LPCWSTR prefix, UString &resultPath) 1.749 +{ 1.750 + UString tempPath; 1.751 + if (!MyGetTempPath(tempPath)) 1.752 + return false; 1.753 + if (Create(tempPath, prefix, resultPath) != 0) 1.754 + return true; 1.755 + if (!MyGetWindowsDirectory(tempPath)) 1.756 + return false; 1.757 + return (Create(tempPath, prefix, resultPath) != 0); 1.758 +} 1.759 + 1.760 +bool CTempFileW::Remove() 1.761 +{ 1.762 + if (!_mustBeDeleted) 1.763 + return true; 1.764 + _mustBeDeleted = !DeleteFileAlways(_fileName); 1.765 + return !_mustBeDeleted; 1.766 +} 1.767 + 1.768 +#endif 1.769 + 1.770 +bool CreateTempDirectory(LPCTSTR prefix, CSysString &dirName) 1.771 +{ 1.772 + /* 1.773 + CSysString prefix = tempPath + prefixChars; 1.774 + CRandom random; 1.775 + random.Init(); 1.776 + */ 1.777 + for (;;) 1.778 + { 1.779 + CTempFile tempFile; 1.780 + if (!tempFile.Create(prefix, dirName)) 1.781 + return false; 1.782 + if (!::DeleteFile(dirName)) 1.783 + return false; 1.784 + /* 1.785 + UINT32 randomNumber = random.Generate(); 1.786 + TCHAR randomNumberString[32]; 1.787 + _stprintf(randomNumberString, _T("%04X"), randomNumber); 1.788 + dirName = prefix + randomNumberString; 1.789 + */ 1.790 + if (NFind::DoesFileExist(dirName)) 1.791 + continue; 1.792 + if (MyCreateDirectory(dirName)) 1.793 + return true; 1.794 + if (::GetLastError() != ERROR_ALREADY_EXISTS) 1.795 + return false; 1.796 + } 1.797 +} 1.798 + 1.799 +bool CTempDirectory::Create(LPCTSTR prefix) 1.800 +{ 1.801 + Remove(); 1.802 + return (_mustBeDeleted = CreateTempDirectory(prefix, _tempDir)); 1.803 +} 1.804 + 1.805 +#ifndef _UNICODE 1.806 + 1.807 +bool CreateTempDirectory(LPCWSTR prefix, UString &dirName) 1.808 +{ 1.809 + /* 1.810 + CSysString prefix = tempPath + prefixChars; 1.811 + CRandom random; 1.812 + random.Init(); 1.813 + */ 1.814 + for (;;) 1.815 + { 1.816 + CTempFileW tempFile; 1.817 + if (!tempFile.Create(prefix, dirName)) 1.818 + return false; 1.819 + if (!DeleteFileAlways(dirName)) 1.820 + return false; 1.821 + /* 1.822 + UINT32 randomNumber = random.Generate(); 1.823 + TCHAR randomNumberString[32]; 1.824 + _stprintf(randomNumberString, _T("%04X"), randomNumber); 1.825 + dirName = prefix + randomNumberString; 1.826 + */ 1.827 + if (NFind::DoesFileExist(dirName)) 1.828 + continue; 1.829 + if (MyCreateDirectory(dirName)) 1.830 + return true; 1.831 + if (::GetLastError() != ERROR_ALREADY_EXISTS) 1.832 + return false; 1.833 + } 1.834 +} 1.835 + 1.836 +bool CTempDirectoryW::Create(LPCWSTR prefix) 1.837 +{ 1.838 + Remove(); 1.839 + return (_mustBeDeleted = CreateTempDirectory(prefix, _tempDir)); 1.840 +} 1.841 + 1.842 +#endif 1.843 + 1.844 +}}}