aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/main/cpp
diff options
context:
space:
mode:
authorGravatar Laszlo Csomor <laszlocsomor@google.com>2016-12-21 15:01:36 +0000
committerGravatar Klaus Aehlig <aehlig@google.com>2016-12-21 17:23:51 +0000
commit7de9b6f1d9748d7347fa76f5ac8d0258c79b6d70 (patch)
treee0fc695c7e65e6d0fcd9f2929de6811afdf7e734 /src/main/cpp
parentfd31061d4cd99277ba1cfacd17ac316f8dfea4f5 (diff)
Bazel client, Windows: implement ReadFile
Implement blaze_util::ReadFile on top of the ::ReadFile Windows API function. Also implement blaze_util::AsWindowsPath so we can convert MSYS paths to Windows widechar paths. Add tests. See https://github.com/bazelbuild/bazel/issues/2107 -- PiperOrigin-RevId: 142659955 MOS_MIGRATED_REVID=142659955
Diffstat (limited to 'src/main/cpp')
-rw-r--r--src/main/cpp/util/file_posix.cc2
-rw-r--r--src/main/cpp/util/file_windows.cc41
2 files changed, 36 insertions, 7 deletions
diff --git a/src/main/cpp/util/file_posix.cc b/src/main/cpp/util/file_posix.cc
index c5568a4c3e..127f811d32 100644
--- a/src/main/cpp/util/file_posix.cc
+++ b/src/main/cpp/util/file_posix.cc
@@ -179,7 +179,6 @@ pair<string, string> SplitPath(const string &path) {
return std::make_pair(string(path, 0, pos), string(path, pos + 1));
}
-#endif // not __CYGWIN__
bool ReadFile(const string &filename, string *content, int max_size) {
int fd = open(filename.c_str(), O_RDONLY);
@@ -190,6 +189,7 @@ bool ReadFile(const string &filename, string *content, int max_size) {
close(fd);
return result;
}
+#endif // not __CYGWIN__
bool WriteFile(const void *data, size_t size, const string &filename) {
UnlinkPath(filename); // We don't care about the success of this.
diff --git a/src/main/cpp/util/file_windows.cc b/src/main/cpp/util/file_windows.cc
index 78cb331185..6ded8c83cf 100644
--- a/src/main/cpp/util/file_windows.cc
+++ b/src/main/cpp/util/file_windows.cc
@@ -217,14 +217,43 @@ bool AsWindowsPath(const string& path, wstring* result) {
return true;
}
-#ifdef COMPILER_MSVC
bool ReadFile(const string& filename, string* content, int max_size) {
- // TODO(bazel-team): implement this.
- pdie(255, "blaze_util::ReadFile is not implemented on Windows");
- return false;
+ wstring wfilename;
+ if (!AsWindowsPath(filename, &wfilename)) {
+ // Failed to convert the path because it was an absolute MSYS path but we
+ // could not retrieve the BAZEL_SH envvar.
+ return false;
+ }
+
+ if (wfilename.size() > MAX_PATH) {
+ // CreateFileW requires that paths longer than MAX_PATH be prefixed with
+ // "\\?\", so add that here.
+ // TODO(laszlocsomor): add a test for this code path.
+ wfilename = wstring(L"\\\\?\\") + wfilename;
+ }
+
+ HANDLE handle = CreateFileW(
+ /* lpFileName */ wfilename.c_str(),
+ /* dwDesiredAccess */ GENERIC_READ,
+ /* dwShareMode */ FILE_SHARE_READ,
+ /* lpSecurityAttributes */ NULL,
+ /* dwCreationDisposition */ OPEN_EXISTING,
+ /* dwFlagsAndAttributes */ FILE_ATTRIBUTE_NORMAL,
+ /* hTemplateFile */ NULL);
+ if (handle == INVALID_HANDLE_VALUE) {
+ return false;
+ }
+
+ bool result = ReadFrom(
+ [handle](void* buf, int len) {
+ DWORD actually_read = 0;
+ ::ReadFile(handle, buf, len, &actually_read, NULL);
+ return actually_read;
+ },
+ content, max_size);
+ CloseHandle(handle);
+ return result;
}
-#else // not COMPILER_MSVC
-#endif // COMPILER_MSVC
#ifdef COMPILER_MSVC
bool WriteFile(const void* data, size_t size, const string& filename) {