1 //===-- LockFileWindows.cpp -------------------------------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #include "lldb/Host/windows/LockFileWindows.h" 10 11 #include <io.h> 12 13 using namespace lldb; 14 using namespace lldb_private; 15 16 namespace { 17 18 Status fileLock(HANDLE file_handle, DWORD flags, const uint64_t start, 19 const uint64_t len) { 20 if (start != 0) 21 return Status("Non-zero start lock regions are not supported"); 22 23 OVERLAPPED overlapped = {}; 24 25 if (!::LockFileEx(file_handle, flags, 0, len, 0, &overlapped) && 26 ::GetLastError() != ERROR_IO_PENDING) 27 return Status(::GetLastError(), eErrorTypeWin32); 28 29 DWORD bytes; 30 if (!::GetOverlappedResult(file_handle, &overlapped, &bytes, TRUE)) 31 return Status(::GetLastError(), eErrorTypeWin32); 32 33 return Status(); 34 } 35 36 } // namespace 37 38 LockFileWindows::LockFileWindows(int fd) 39 : LockFileBase(fd), m_file(reinterpret_cast<HANDLE>(_get_osfhandle(fd))) {} 40 41 LockFileWindows::~LockFileWindows() { Unlock(); } 42 43 bool LockFileWindows::IsValidFile() const { 44 return LockFileBase::IsValidFile() && m_file != INVALID_HANDLE_VALUE; 45 } 46 47 Status LockFileWindows::DoWriteLock(const uint64_t start, const uint64_t len) { 48 return fileLock(m_file, LOCKFILE_EXCLUSIVE_LOCK, start, len); 49 } 50 51 Status LockFileWindows::DoTryWriteLock(const uint64_t start, 52 const uint64_t len) { 53 return fileLock(m_file, LOCKFILE_EXCLUSIVE_LOCK | LOCKFILE_FAIL_IMMEDIATELY, 54 start, len); 55 } 56 57 Status LockFileWindows::DoReadLock(const uint64_t start, const uint64_t len) { 58 return fileLock(m_file, 0, start, len); 59 } 60 61 Status LockFileWindows::DoTryReadLock(const uint64_t start, 62 const uint64_t len) { 63 return fileLock(m_file, LOCKFILE_FAIL_IMMEDIATELY, start, len); 64 } 65 66 Status LockFileWindows::DoUnlock() { 67 OVERLAPPED overlapped = {}; 68 69 if (!::UnlockFileEx(m_file, 0, m_len, 0, &overlapped) && 70 ::GetLastError() != ERROR_IO_PENDING) 71 return Status(::GetLastError(), eErrorTypeWin32); 72 73 DWORD bytes; 74 if (!::GetOverlappedResult(m_file, &overlapped, &bytes, TRUE)) 75 return Status(::GetLastError(), eErrorTypeWin32); 76 77 return Status(); 78 } 79