diff options
Diffstat (limited to 'Source/kwsys/SystemTools.cxx')
-rw-r--r-- | Source/kwsys/SystemTools.cxx | 428 |
1 files changed, 277 insertions, 151 deletions
diff --git a/Source/kwsys/SystemTools.cxx b/Source/kwsys/SystemTools.cxx index 6144d9c..f610a70 100644 --- a/Source/kwsys/SystemTools.cxx +++ b/Source/kwsys/SystemTools.cxx @@ -14,6 +14,10 @@ # endif #endif +#if defined(_WIN32) && !defined(_WIN32_WINNT) +# define _WIN32_WINNT _WIN32_WINNT_VISTA +#endif + #include "kwsysPrivate.h" #include KWSYS_HEADER(RegularExpression.hxx) #include KWSYS_HEADER(SystemTools.hxx) @@ -93,9 +97,43 @@ # ifndef INVALID_FILE_ATTRIBUTES # define INVALID_FILE_ATTRIBUTES ((DWORD)-1) # endif +# ifndef SYMBOLIC_LINK_FLAG_ALLOW_UNPRIVILEGED_CREATE +# define SYMBOLIC_LINK_FLAG_ALLOW_UNPRIVILEGED_CREATE (0x2) +# endif # if defined(_MSC_VER) && _MSC_VER >= 1800 # define KWSYS_WINDOWS_DEPRECATED_GetVersionEx # endif +// from ntifs.h, which can only be used by drivers +typedef struct _REPARSE_DATA_BUFFER +{ + ULONG ReparseTag; + USHORT ReparseDataLength; + USHORT Reserved; + union + { + struct + { + USHORT SubstituteNameOffset; + USHORT SubstituteNameLength; + USHORT PrintNameOffset; + USHORT PrintNameLength; + ULONG Flags; + WCHAR PathBuffer[1]; + } SymbolicLinkReparseBuffer; + struct + { + USHORT SubstituteNameOffset; + USHORT SubstituteNameLength; + USHORT PrintNameOffset; + USHORT PrintNameLength; + WCHAR PathBuffer[1]; + } MountPointReparseBuffer; + struct + { + UCHAR DataBuffer[1]; + } GenericReparseBuffer; + } DUMMYUNIONNAME; +} REPARSE_DATA_BUFFER, *PREPARSE_DATA_BUFFER; #endif #if !KWSYS_CXX_HAS_ENVIRON_IN_STDLIB_H @@ -244,7 +282,7 @@ inline int Chdir(const std::string& dir) return _wchdir(KWSYS_NAMESPACE::Encoding::ToWide(dir).c_str()); } inline void Realpath(const std::string& path, std::string& resolved_path, - std::string* errorMessage = 0) + std::string* errorMessage = nullptr) { std::wstring tmp = KWSYS_NAMESPACE::Encoding::ToWide(path); wchar_t* ptemp; @@ -882,21 +920,24 @@ FILE* SystemTools::Fopen(const std::string& file, const char* mode) #endif } -bool SystemTools::MakeDirectory(const char* path, const mode_t* mode) +Status SystemTools::MakeDirectory(const char* path, const mode_t* mode) { if (!path) { - return false; + return Status::POSIX(EINVAL); } return SystemTools::MakeDirectory(std::string(path), mode); } -bool SystemTools::MakeDirectory(const std::string& path, const mode_t* mode) +Status SystemTools::MakeDirectory(std::string const& path, const mode_t* mode) { - if (SystemTools::PathExists(path)) { - return SystemTools::FileIsDirectory(path); - } if (path.empty()) { - return false; + return Status::POSIX(EINVAL); + } + if (SystemTools::PathExists(path)) { + if (SystemTools::FileIsDirectory(path)) { + return Status::Success(); + } + return Status::POSIX(EEXIST); } std::string dir = path; SystemTools::ConvertToUnixSlashes(dir); @@ -914,15 +955,11 @@ bool SystemTools::MakeDirectory(const std::string& path, const mode_t* mode) ++pos; } topdir = dir; - if (Mkdir(topdir, mode) != 0) { - // if it is some other error besides directory exists - // then return false - if (errno != EEXIST) { - return false; - } + if (Mkdir(topdir, mode) != 0 && errno != EEXIST) { + return Status::POSIX_errno(); } - return true; + return Status::Success(); } // replace replace with with as many times as it shows up in source. @@ -1411,18 +1448,18 @@ int SystemTools::Stat(const std::string& path, SystemTools::Stat_t* buf) #endif } -bool SystemTools::Touch(const std::string& filename, bool create) +Status SystemTools::Touch(std::string const& filename, bool create) { if (!SystemTools::FileExists(filename)) { if (create) { FILE* file = Fopen(filename, "a+b"); if (file) { fclose(file); - return true; + return Status::Success(); } - return false; + return Status::POSIX_errno(); } else { - return true; + return Status::Success(); } } #if defined(_WIN32) && !defined(__CYGWIN__) @@ -1430,31 +1467,32 @@ bool SystemTools::Touch(const std::string& filename, bool create) FILE_WRITE_ATTRIBUTES, FILE_SHARE_WRITE, 0, OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS, 0); if (!h) { - return false; + return Status::Windows_GetLastError(); } FILETIME mtime; GetSystemTimeAsFileTime(&mtime); if (!SetFileTime(h, 0, 0, &mtime)) { + Status status = Status::Windows_GetLastError(); CloseHandle(h); - return false; + return status; } CloseHandle(h); #elif KWSYS_CXX_HAS_UTIMENSAT // utimensat is only available on newer Unixes and macOS 10.13+ if (utimensat(AT_FDCWD, filename.c_str(), nullptr, 0) < 0) { - return false; + return Status::POSIX_errno(); } #else // fall back to utimes if (utimes(filename.c_str(), nullptr) < 0) { - return false; + return Status::POSIX_errno(); } #endif - return true; + return Status::Success(); } -bool SystemTools::FileTimeCompare(const std::string& f1, const std::string& f2, - int* result) +Status SystemTools::FileTimeCompare(std::string const& f1, + std::string const& f2, int* result) { // Default to same time. *result = 0; @@ -1462,11 +1500,11 @@ bool SystemTools::FileTimeCompare(const std::string& f1, const std::string& f2, // POSIX version. Use stat function to get file modification time. struct stat s1; if (stat(f1.c_str(), &s1) != 0) { - return false; + return Status::POSIX_errno(); } struct stat s2; if (stat(f2.c_str(), &s2) != 0) { - return false; + return Status::POSIX_errno(); } # if KWSYS_CXX_STAT_HAS_ST_MTIM // Compare using nanosecond resolution. @@ -1504,17 +1542,17 @@ bool SystemTools::FileTimeCompare(const std::string& f1, const std::string& f2, WIN32_FILE_ATTRIBUTE_DATA f2d; if (!GetFileAttributesExW(Encoding::ToWindowsExtendedPath(f1).c_str(), GetFileExInfoStandard, &f1d)) { - return false; + return Status::Windows_GetLastError(); } if (!GetFileAttributesExW(Encoding::ToWindowsExtendedPath(f2).c_str(), GetFileExInfoStandard, &f2d)) { - return false; + return Status::Windows_GetLastError(); } // Compare the file times using resolution provided by system call. *result = (int)CompareFileTime(&f1d.ftLastWriteTime, &f2d.ftLastWriteTime); #endif - return true; + return Status::Success(); } // Return a capitalized string (i.e the first letter is uppercased, all other @@ -2129,8 +2167,8 @@ static std::string FileInDir(const std::string& source, const std::string& dir) return new_destination + '/' + SystemTools::GetFilenameName(source); } -bool SystemTools::CopyFileIfDifferent(const std::string& source, - const std::string& destination) +Status SystemTools::CopyFileIfDifferent(std::string const& source, + std::string const& destination) { // special check for a destination that is a directory // FilesDiffer does not handle file to directory compare @@ -2147,7 +2185,7 @@ bool SystemTools::CopyFileIfDifferent(const std::string& source, } } // at this point the files must be the same so return true - return true; + return Status::Success(); } #define KWSYS_ST_BUFFER 4096 @@ -2273,16 +2311,13 @@ bool SystemTools::TextFilesDiffer(const std::string& path1, return false; } -/** - * Blockwise copy source to destination file - */ -static bool CopyFileContentBlockwise(const std::string& source, - const std::string& destination) +Status SystemTools::CopyFileContentBlockwise(std::string const& source, + std::string const& destination) { // Open files kwsys::ifstream fin(source.c_str(), std::ios::in | std::ios::binary); if (!fin) { - return false; + return Status::POSIX_errno(); } // try and remove the destination file so that read only destination files @@ -2294,7 +2329,7 @@ static bool CopyFileContentBlockwise(const std::string& source, kwsys::ofstream fout(destination.c_str(), std::ios::out | std::ios::trunc | std::ios::binary); if (!fout) { - return false; + return Status::POSIX_errno(); } // This copy loop is very sensitive on certain platforms with @@ -2323,10 +2358,10 @@ static bool CopyFileContentBlockwise(const std::string& source, fout.close(); if (!fout) { - return false; + return Status::POSIX_errno(); } - return true; + return Status::Success(); } /** @@ -2341,13 +2376,13 @@ static bool CopyFileContentBlockwise(const std::string& source, * - The underlying filesystem does not support file cloning * - An unspecified error occurred */ -static bool CloneFileContent(const std::string& source, - const std::string& destination) +Status SystemTools::CloneFileContent(std::string const& source, + std::string const& destination) { #if defined(__linux) && defined(FICLONE) int in = open(source.c_str(), O_RDONLY); if (in < 0) { - return false; + return Status::POSIX_errno(); } SystemTools::RemoveFile(destination); @@ -2355,38 +2390,42 @@ static bool CloneFileContent(const std::string& source, int out = open(destination.c_str(), O_WRONLY | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR); if (out < 0) { + Status status = Status::POSIX_errno(); close(in); - return false; + return status; } - int result = ioctl(out, FICLONE, in); + Status status = Status::Success(); + if (ioctl(out, FICLONE, in) < 0) { + status = Status::POSIX_errno(); + } close(in); close(out); - if (result < 0) { - return false; - } - - return true; + return status; #else (void)source; (void)destination; - return false; + return Status::POSIX(ENOSYS); #endif } /** * Copy a file named by "source" to the file named by "destination". */ -bool SystemTools::CopyFileAlways(const std::string& source, - const std::string& destination) +Status SystemTools::CopyFileAlways(std::string const& source, + std::string const& destination) { + Status status; mode_t perm = 0; - bool perms = SystemTools::GetPermissions(source, perm); + Status perms = SystemTools::GetPermissions(source, perm); std::string real_destination = destination; if (SystemTools::FileIsDirectory(source)) { - SystemTools::MakeDirectory(destination); + status = SystemTools::MakeDirectory(destination); + if (!status) { + return status; + } } else { // If destination is a directory, try to create a file with the same // name as the source in that directory. @@ -2403,30 +2442,34 @@ bool SystemTools::CopyFileAlways(const std::string& source, } // If files are the same do not copy if (SystemTools::SameFile(source, real_destination)) { - return true; + return status; } // Create destination directory - - SystemTools::MakeDirectory(destination_dir); - - if (!CloneFileContent(source, real_destination)) { - // if cloning did not succeed, fall back to blockwise copy - if (!CopyFileContentBlockwise(source, real_destination)) { - return false; + if (!destination_dir.empty()) { + status = SystemTools::MakeDirectory(destination_dir); + if (!status) { + return status; } } + + status = SystemTools::CloneFileContent(source, real_destination); + // if cloning did not succeed, fall back to blockwise copy + if (!status) { + status = SystemTools::CopyFileContentBlockwise(source, real_destination); + } + if (!status) { + return status; + } } if (perms) { - if (!SystemTools::SetPermissions(real_destination, perm)) { - return false; - } + status = SystemTools::SetPermissions(real_destination, perm); } - return true; + return status; } -bool SystemTools::CopyAFile(const std::string& source, - const std::string& destination, bool always) +Status SystemTools::CopyAFile(std::string const& source, + std::string const& destination, bool always) { if (always) { return SystemTools::CopyFileAlways(source, destination); @@ -2439,18 +2482,21 @@ bool SystemTools::CopyAFile(const std::string& source, * Copy a directory content from "source" directory to the directory named by * "destination". */ -bool SystemTools::CopyADirectory(const std::string& source, - const std::string& destination, bool always) +Status SystemTools::CopyADirectory(std::string const& source, + std::string const& destination, bool always) { + Status status; Directory dir; - if (dir.Load(source) == 0) { - return false; + status = dir.Load(source); + if (!status) { + return status; } - size_t fileNum; - if (!SystemTools::MakeDirectory(destination)) { - return false; + status = SystemTools::MakeDirectory(destination); + if (!status) { + return status; } - for (fileNum = 0; fileNum < dir.GetNumberOfFiles(); ++fileNum) { + + for (size_t fileNum = 0; fileNum < dir.GetNumberOfFiles(); ++fileNum) { if (strcmp(dir.GetFile(static_cast<unsigned long>(fileNum)), ".") != 0 && strcmp(dir.GetFile(static_cast<unsigned long>(fileNum)), "..") != 0) { std::string fullPath = source; @@ -2460,18 +2506,20 @@ bool SystemTools::CopyADirectory(const std::string& source, std::string fullDestPath = destination; fullDestPath += "/"; fullDestPath += dir.GetFile(static_cast<unsigned long>(fileNum)); - if (!SystemTools::CopyADirectory(fullPath, fullDestPath, always)) { - return false; + status = SystemTools::CopyADirectory(fullPath, fullDestPath, always); + if (!status) { + return status; } } else { - if (!SystemTools::CopyAFile(fullPath, destination, always)) { - return false; + status = SystemTools::CopyAFile(fullPath, destination, always); + if (!status) { + return status; } } } } - return true; + return status; } // return size of file; also returns zero if no file exists @@ -2553,26 +2601,26 @@ std::string SystemTools::GetLastSystemError() return strerror(e); } -bool SystemTools::RemoveFile(const std::string& source) +Status SystemTools::RemoveFile(std::string const& source) { #ifdef _WIN32 std::wstring const& ws = Encoding::ToWindowsExtendedPath(source); if (DeleteFileW(ws.c_str())) { - return true; + return Status::Success(); } DWORD err = GetLastError(); if (err == ERROR_FILE_NOT_FOUND || err == ERROR_PATH_NOT_FOUND) { - return true; + return Status::Success(); } if (err != ERROR_ACCESS_DENIED) { - return false; + return Status::Windows(err); } /* The file may be read-only. Try adding write permission. */ mode_t mode; if (!SystemTools::GetPermissions(source, mode) || !SystemTools::SetPermissions(source, S_IWRITE)) { SetLastError(err); - return false; + return Status::Windows(err); } const DWORD DIRECTORY_SOFT_LINK_ATTRS = @@ -2581,26 +2629,29 @@ bool SystemTools::RemoveFile(const std::string& source) if (attrs != INVALID_FILE_ATTRIBUTES && (attrs & DIRECTORY_SOFT_LINK_ATTRS) == DIRECTORY_SOFT_LINK_ATTRS && RemoveDirectoryW(ws.c_str())) { - return true; + return Status::Success(); } if (DeleteFileW(ws.c_str()) || GetLastError() == ERROR_FILE_NOT_FOUND || GetLastError() == ERROR_PATH_NOT_FOUND) { - return true; + return Status::Success(); } /* Try to restore the original permissions. */ SystemTools::SetPermissions(source, mode); SetLastError(err); - return false; + return Status::Windows(err); #else - return unlink(source.c_str()) == 0 || errno == ENOENT; + if (unlink(source.c_str()) != 0 && errno != ENOENT) { + return Status::POSIX_errno(); + } + return Status::Success(); #endif } -bool SystemTools::RemoveADirectory(const std::string& source) +Status SystemTools::RemoveADirectory(std::string const& source) { // Add write permission to the directory so we can modify its // content to remove files and directories from it. - mode_t mode; + mode_t mode = 0; if (SystemTools::GetPermissions(source, mode)) { #if defined(_WIN32) && !defined(__CYGWIN__) mode |= S_IWRITE; @@ -2610,8 +2661,13 @@ bool SystemTools::RemoveADirectory(const std::string& source) SystemTools::SetPermissions(source, mode); } + Status status; Directory dir; - dir.Load(source); + status = dir.Load(source); + if (!status) { + return status; + } + size_t fileNum; for (fileNum = 0; fileNum < dir.GetNumberOfFiles(); ++fileNum) { if (strcmp(dir.GetFile(static_cast<unsigned long>(fileNum)), ".") != 0 && @@ -2621,18 +2677,23 @@ bool SystemTools::RemoveADirectory(const std::string& source) fullPath += dir.GetFile(static_cast<unsigned long>(fileNum)); if (SystemTools::FileIsDirectory(fullPath) && !SystemTools::FileIsSymlink(fullPath)) { - if (!SystemTools::RemoveADirectory(fullPath)) { - return false; + status = SystemTools::RemoveADirectory(fullPath); + if (!status) { + return status; } } else { - if (!SystemTools::RemoveFile(fullPath)) { - return false; + status = SystemTools::RemoveFile(fullPath); + if (!status) { + return status; } } } } - return (Rmdir(source) == 0); + if (Rmdir(source) != 0) { + status = Status::POSIX_errno(); + } + return status; } /** @@ -2985,7 +3046,7 @@ bool SystemTools::FileIsSymlink(const std::string& name) } CloseHandle(hFile); ULONG reparseTag = - reinterpret_cast<PREPARSE_GUID_DATA_BUFFER>(&buffer[0])->ReparseTag; + reinterpret_cast<PREPARSE_DATA_BUFFER>(&buffer[0])->ReparseTag; return (reparseTag == IO_REPARSE_TAG_SYMLINK) || (reparseTag == IO_REPARSE_TAG_MOUNT_POINT); } @@ -3025,45 +3086,109 @@ bool SystemTools::FileIsFIFO(const std::string& name) #endif } -#if defined(_WIN32) && !defined(__CYGWIN__) -bool SystemTools::CreateSymlink(const std::string&, const std::string&) +Status SystemTools::CreateSymlink(std::string const& origName, + std::string const& newName) { - return false; -} +#if defined(_WIN32) && !defined(__CYGWIN__) + DWORD flags; + if (FileIsDirectory(origName)) { + flags = SYMBOLIC_LINK_FLAG_DIRECTORY; + } else { + flags = 0; + } + + std::wstring origPath = Encoding::ToWindowsExtendedPath(origName); + std::wstring newPath = Encoding::ToWindowsExtendedPath(newName); + + Status status; + if (!CreateSymbolicLinkW(newPath.c_str(), origPath.c_str(), + flags | + SYMBOLIC_LINK_FLAG_ALLOW_UNPRIVILEGED_CREATE)) { + status = Status::Windows_GetLastError(); + } + // Older Windows versions do not understand + // SYMBOLIC_LINK_FLAG_ALLOW_UNPRIVILEGED_CREATE + if (status.GetWindows() == ERROR_INVALID_PARAMETER) { + status = Status::Success(); + if (!CreateSymbolicLinkW(newPath.c_str(), origPath.c_str(), flags)) { + status = Status::Windows_GetLastError(); + } + } + + return status; #else -bool SystemTools::CreateSymlink(const std::string& origName, - const std::string& newName) -{ - return symlink(origName.c_str(), newName.c_str()) >= 0; -} + if (symlink(origName.c_str(), newName.c_str()) < 0) { + return Status::POSIX_errno(); + } + return Status::Success(); #endif +} -#if defined(_WIN32) && !defined(__CYGWIN__) -bool SystemTools::ReadSymlink(const std::string&, std::string&) +Status SystemTools::ReadSymlink(std::string const& newName, + std::string& origName) { - return false; -} +#if defined(_WIN32) && !defined(__CYGWIN__) + std::wstring newPath = Encoding::ToWindowsExtendedPath(newName); + // FILE_ATTRIBUTE_REPARSE_POINT means: + // * a file or directory that has an associated reparse point, or + // * a file that is a symbolic link. + HANDLE hFile = CreateFileW( + newPath.c_str(), GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, + FILE_FLAG_OPEN_REPARSE_POINT | FILE_FLAG_BACKUP_SEMANTICS, nullptr); + if (hFile == INVALID_HANDLE_VALUE) { + return Status::Windows_GetLastError(); + } + byte buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE]; + DWORD bytesReturned = 0; + Status status; + if (!DeviceIoControl(hFile, FSCTL_GET_REPARSE_POINT, nullptr, 0, buffer, + MAXIMUM_REPARSE_DATA_BUFFER_SIZE, &bytesReturned, + nullptr)) { + status = Status::Windows_GetLastError(); + } + CloseHandle(hFile); + if (!status) { + return status; + } + PREPARSE_DATA_BUFFER data = + reinterpret_cast<PREPARSE_DATA_BUFFER>(&buffer[0]); + USHORT substituteNameLength; + PCWSTR substituteNameData; + if (data->ReparseTag == IO_REPARSE_TAG_SYMLINK) { + substituteNameLength = + data->SymbolicLinkReparseBuffer.SubstituteNameLength / sizeof(WCHAR); + substituteNameData = data->SymbolicLinkReparseBuffer.PathBuffer + + data->SymbolicLinkReparseBuffer.SubstituteNameOffset / sizeof(WCHAR); + } else if (data->ReparseTag == IO_REPARSE_TAG_MOUNT_POINT) { + substituteNameLength = + data->MountPointReparseBuffer.SubstituteNameLength / sizeof(WCHAR); + substituteNameData = data->MountPointReparseBuffer.PathBuffer + + data->MountPointReparseBuffer.SubstituteNameOffset / sizeof(WCHAR); + } else { + return Status::Windows(ERROR_REPARSE_TAG_MISMATCH); + } + std::wstring substituteName(substituteNameData, substituteNameLength); + origName = Encoding::ToNarrow(substituteName); #else -bool SystemTools::ReadSymlink(const std::string& newName, - std::string& origName) -{ char buf[KWSYS_SYSTEMTOOLS_MAXPATH + 1]; int count = static_cast<int>( readlink(newName.c_str(), buf, KWSYS_SYSTEMTOOLS_MAXPATH)); - if (count >= 0) { - // Add null-terminator. - buf[count] = 0; - origName = buf; - return true; - } else { - return false; + if (count < 0) { + return Status::POSIX_errno(); } -} + // Add null-terminator. + buf[count] = 0; + origName = buf; #endif + return Status::Success(); +} -int SystemTools::ChangeDirectory(const std::string& dir) +Status SystemTools::ChangeDirectory(std::string const& dir) { - return Chdir(dir); + if (Chdir(dir) < 0) { + return Status::POSIX_errno(); + } + return Status::Success(); } std::string SystemTools::GetCurrentWorkingDirectory() @@ -3929,7 +4054,7 @@ bool SystemTools::FileIsFullPath(const char* in_name) bool SystemToolsStatic::FileIsFullPath(const char* in_name, size_t len) { -#if defined(_WIN32) || defined(__CYGWIN__) +#if defined(_WIN32) && !defined(__CYGWIN__) // On Windows, the name must be at least two characters long. if (len < 2) { return false; @@ -3960,7 +4085,8 @@ bool SystemToolsStatic::FileIsFullPath(const char* in_name, size_t len) return false; } -bool SystemTools::GetShortPath(const std::string& path, std::string& shortPath) +Status SystemTools::GetShortPath(std::string const& path, + std::string& shortPath) { #if defined(_WIN32) && !defined(__CYGWIN__) std::string tempPath = path; // create a buffer @@ -3980,14 +4106,14 @@ bool SystemTools::GetShortPath(const std::string& path, std::string& shortPath) } if (ret == 0) { - return false; + return Status::Windows_GetLastError(); } else { shortPath = Encoding::ToNarrow(&buffer[0]); - return true; + return Status::Success(); } #else shortPath = path; - return true; + return Status::Success(); #endif } @@ -4088,21 +4214,21 @@ int SystemTools::GetTerminalWidth() return width; } -bool SystemTools::GetPermissions(const char* file, mode_t& mode) +Status SystemTools::GetPermissions(const char* file, mode_t& mode) { if (!file) { - return false; + return Status::POSIX(EINVAL); } return SystemTools::GetPermissions(std::string(file), mode); } -bool SystemTools::GetPermissions(const std::string& file, mode_t& mode) +Status SystemTools::GetPermissions(std::string const& file, mode_t& mode) { #if defined(_WIN32) DWORD attr = GetFileAttributesW(Encoding::ToWindowsExtendedPath(file).c_str()); if (attr == INVALID_FILE_ATTRIBUTES) { - return false; + return Status::Windows_GetLastError(); } if ((attr & FILE_ATTRIBUTE_READONLY) != 0) { mode = (_S_IREAD | (_S_IREAD >> 3) | (_S_IREAD >> 6)); @@ -4125,27 +4251,27 @@ bool SystemTools::GetPermissions(const std::string& file, mode_t& mode) #else struct stat st; if (stat(file.c_str(), &st) < 0) { - return false; + return Status::POSIX_errno(); } mode = st.st_mode; #endif - return true; + return Status::Success(); } -bool SystemTools::SetPermissions(const char* file, mode_t mode, - bool honor_umask) +Status SystemTools::SetPermissions(const char* file, mode_t mode, + bool honor_umask) { if (!file) { - return false; + return Status::POSIX(EINVAL); } return SystemTools::SetPermissions(std::string(file), mode, honor_umask); } -bool SystemTools::SetPermissions(const std::string& file, mode_t mode, - bool honor_umask) +Status SystemTools::SetPermissions(std::string const& file, mode_t mode, + bool honor_umask) { if (!SystemTools::PathExists(file)) { - return false; + return Status::POSIX(ENOENT); } if (honor_umask) { mode_t currentMask = umask(0); @@ -4158,10 +4284,10 @@ bool SystemTools::SetPermissions(const std::string& file, mode_t mode, if (chmod(file.c_str(), mode) < 0) #endif { - return false; + return Status::POSIX_errno(); } - return true; + return Status::Success(); } std::string SystemTools::GetParentDirectory(const std::string& fileOrDir) @@ -4238,7 +4364,7 @@ std::string SystemTools::GetOperatingSystemNameAndVersion() # endif bOsVersionInfoEx = GetVersionExA((OSVERSIONINFOA*)&osvi); if (!bOsVersionInfoEx) { - return 0; + return ""; } # ifdef KWSYS_WINDOWS_DEPRECATED_GetVersionEx # ifdef __clang__ @@ -4377,14 +4503,14 @@ std::string SystemTools::GetOperatingSystemNameAndVersion() L"SYSTEM\\CurrentControlSet\\Control\\ProductOptions", 0, KEY_QUERY_VALUE, &hKey); if (lRet != ERROR_SUCCESS) { - return 0; + return ""; } lRet = RegQueryValueExW(hKey, L"ProductType", nullptr, nullptr, (LPBYTE)szProductType, &dwBufLen); if ((lRet != ERROR_SUCCESS) || (dwBufLen > BUFSIZE)) { - return 0; + return ""; } RegCloseKey(hKey); |