1 //===-- HostThreadWindows.cpp -----------------------------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #include "lldb/Core/Error.h"
11 
12 #include "lldb/Host/windows/windows.h"
13 #include "lldb/Host/windows/HostThreadWindows.h"
14 
15 #include "llvm/ADT/STLExtras.h"
16 
17 using namespace lldb;
18 using namespace lldb_private;
19 
20 HostThreadWindows::HostThreadWindows()
21     : HostNativeThreadBase()
22     , m_owns_handle(true)
23 {
24 }
25 
26 HostThreadWindows::HostThreadWindows(lldb::thread_t thread)
27     : HostNativeThreadBase(thread)
28     , m_owns_handle(true)
29 {
30 }
31 
32 HostThreadWindows::~HostThreadWindows()
33 {
34     Reset();
35 }
36 
37 void
38 HostThreadWindows::SetOwnsHandle(bool owns)
39 {
40     m_owns_handle = owns;
41 }
42 
43 Error
44 HostThreadWindows::Join(lldb::thread_result_t *result)
45 {
46     Error error;
47     if (IsJoinable())
48     {
49         DWORD wait_result = ::WaitForSingleObject(m_thread, INFINITE);
50         if (WAIT_OBJECT_0 == wait_result && result)
51         {
52             DWORD exit_code = 0;
53             if (!::GetExitCodeThread(m_thread, &exit_code))
54                 *result = 0;
55             *result = exit_code;
56         }
57         else if (WAIT_OBJECT_0 != wait_result)
58             error.SetError(::GetLastError(), eErrorTypeWin32);
59     }
60     else
61         error.SetError(ERROR_INVALID_HANDLE, eErrorTypeWin32);
62 
63     Reset ();
64     return error;
65 }
66 
67 Error
68 HostThreadWindows::Cancel()
69 {
70     Error error;
71 
72     DWORD result = ::QueueUserAPC(::ExitThread, m_thread, 0);
73     error.SetError(result, eErrorTypeWin32);
74     return error;
75 }
76 
77 lldb::tid_t
78 HostThreadWindows::GetThreadId() const
79 {
80     return ::GetThreadId(m_thread);
81 }
82 
83 void
84 HostThreadWindows::Reset()
85 {
86     if (m_owns_handle && m_thread != LLDB_INVALID_HOST_THREAD)
87         ::CloseHandle(m_thread);
88 
89     HostNativeThreadBase::Reset();
90 }
91