]> git.cworth.org Git - vogl/blob - src/voglcore/lzma_Threads.cpp
Initial vogl checkin
[vogl] / src / voglcore / lzma_Threads.cpp
1 /**************************************************************************
2  *
3  * Copyright 2013-2014 RAD Game Tools and Valve Software
4  * Copyright 2010-2014 Rich Geldreich and Tenacious Software LLC
5  * All Rights Reserved.
6  *
7  * Permission is hereby granted, free of charge, to any person obtaining a copy
8  * of this software and associated documentation files (the "Software"), to deal
9  * in the Software without restriction, including without limitation the rights
10  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11  * copies of the Software, and to permit persons to whom the Software is
12  * furnished to do so, subject to the following conditions:
13  *
14  * The above copyright notice and this permission notice shall be included in
15  * all copies or substantial portions of the Software.
16  *
17  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
23  * THE SOFTWARE.
24  *
25  **************************************************************************/
26
27 /* Threads.c -- multithreading library
28 2008-08-05
29 Igor Pavlov
30 Public domain */
31 #include "vogl_core.h"
32 #include "lzma_Threads.h"
33 #include <process.h>
34
35 namespace vogl
36 {
37
38     static WRes GetError()
39     {
40         DWORD res = GetLastError();
41         return (res) ? (WRes)(res) : 1;
42     }
43
44     WRes HandleToWRes(HANDLE h)
45     {
46         return (h != 0) ? 0 : GetError();
47     }
48     WRes BOOLToWRes(BOOL v)
49     {
50         return v ? 0 : GetError();
51     }
52
53     static WRes MyCloseHandle(HANDLE *h)
54     {
55         if (*h != NULL)
56             if (!CloseHandle(*h))
57                 return GetError();
58         *h = NULL;
59         return 0;
60     }
61
62     WRes Thread_Create(CThread *thread, THREAD_FUNC_RET_TYPE(THREAD_FUNC_CALL_TYPE *startAddress)(void *), LPVOID parameter)
63     {
64         unsigned threadId; /* Windows Me/98/95: threadId parameter may not be NULL in _beginthreadex/CreateThread functions */
65         thread->handle =
66             /* CreateThread(0, 0, startAddress, parameter, 0, &threadId); */
67             (HANDLE)_beginthreadex(NULL, 0, startAddress, parameter, 0, &threadId);
68         /* maybe we must use errno here, but probably GetLastError() is also OK. */
69         return HandleToWRes(thread->handle);
70     }
71
72     WRes WaitObject(HANDLE h)
73     {
74         return (WRes)WaitForSingleObject(h, INFINITE);
75     }
76
77     WRes Thread_Wait(CThread *thread)
78     {
79         if (thread->handle == NULL)
80             return 1;
81         return WaitObject(thread->handle);
82     }
83
84     WRes Thread_Close(CThread *thread)
85     {
86         return MyCloseHandle(&thread->handle);
87     }
88
89     WRes Event_Create(CEvent *p, BOOL manualReset, int initialSignaled)
90     {
91         p->handle = CreateEvent(NULL, manualReset, (initialSignaled ? TRUE : FALSE), NULL);
92         return HandleToWRes(p->handle);
93     }
94
95     WRes ManualResetEvent_Create(CManualResetEvent *p, int initialSignaled)
96     {
97         return Event_Create(p, TRUE, initialSignaled);
98     }
99     WRes ManualResetEvent_CreateNotSignaled(CManualResetEvent *p)
100     {
101         return ManualResetEvent_Create(p, 0);
102     }
103
104     WRes AutoResetEvent_Create(CAutoResetEvent *p, int initialSignaled)
105     {
106         return Event_Create(p, FALSE, initialSignaled);
107     }
108     WRes AutoResetEvent_CreateNotSignaled(CAutoResetEvent *p)
109     {
110         return AutoResetEvent_Create(p, 0);
111     }
112
113     WRes Event_Set(CEvent *p)
114     {
115         return BOOLToWRes(SetEvent(p->handle));
116     }
117     WRes Event_Reset(CEvent *p)
118     {
119         return BOOLToWRes(ResetEvent(p->handle));
120     }
121     WRes Event_Wait(CEvent *p)
122     {
123         return WaitObject(p->handle);
124     }
125     WRes Event_Close(CEvent *p)
126     {
127         return MyCloseHandle(&p->handle);
128     }
129
130     WRes Semaphore_Create(CSemaphore *p, UInt32 initiallyCount, UInt32 maxCount)
131     {
132         p->handle = CreateSemaphore(NULL, (LONG)initiallyCount, (LONG)maxCount, NULL);
133         return HandleToWRes(p->handle);
134     }
135
136     WRes Semaphore_Release(CSemaphore *p, LONG releaseCount, LONG *previousCount)
137     {
138         return BOOLToWRes(ReleaseSemaphore(p->handle, releaseCount, previousCount));
139     }
140     WRes Semaphore_ReleaseN(CSemaphore *p, UInt32 releaseCount)
141     {
142         return Semaphore_Release(p, (LONG)releaseCount, NULL);
143     }
144     WRes Semaphore_Release1(CSemaphore *p)
145     {
146         return Semaphore_ReleaseN(p, 1);
147     }
148
149     WRes Semaphore_Wait(CSemaphore *p)
150     {
151         return WaitObject(p->handle);
152     }
153     WRes Semaphore_Close(CSemaphore *p)
154     {
155         return MyCloseHandle(&p->handle);
156     }
157
158     WRes CriticalSection_Init(CCriticalSection *p)
159     {
160 #ifdef _MSC_VER
161         /* InitializeCriticalSection can raise only STATUS_NO_MEMORY exception */
162         __try
163         {
164             InitializeCriticalSection(p);
165             /* InitializeCriticalSectionAndSpinCount(p, 0); */
166         }
167         __except(EXCEPTION_EXECUTE_HANDLER)
168         {
169             return 1;
170         }
171 #else
172         InitializeCriticalSection(p);
173 #endif
174         return 0;
175     }
176 }