Mercurial > sdl-ios-xcode
annotate src/thread/win32/win_ce_semaphore.c @ 1287:15a89a0c52bf
Date: Tue, 15 Feb 2005 21:28:48 +0900 (JST)
From: "Michael Leonhard"
Subject: [SDL] resize bug on Win32 and patch
This is my first post to this mailing list. In this email I will detail a
bug in the behavior of resizable SDL windows on Win32. Then I will
explain the solution and provide a patch.
Symptoms:
Under Windows, an SDL display created with the SDL_RESIZABLE flag exhibits
quirky behavior when being maximized. The window is resized to the proper
size, but it is shifted upwards about half the height of the title bar.
Similarly, a window whose origin is above the top of the screen will
spontaneously move its upper-left origin upon being resized. After two
such resize-induced moves, the title bar will be entirely off the top edge
of the screen. Subsequently, when the mouse is clicked and released on
the window border, the window will shrink its height spontaneously. This
height shrinkage occurs even if the user did not resize the border.
To observe this curious situation, please invoke:
SDL-1.2.8/test/testwm.exe -resize
Cause:
A pair of integers, SDL_windowX and SDL_windowY, are defined in
video/wincommon/SDL_sysevents.c. They are used by the DirectX video
driver and the DIB video driver:
video/windx5/SDL_dx5video.c
video/windib/SDL_dibvideo.c
As I understand the source code, the primary use of these variables is to
create a rectangle that represents the surface area in CLIENT SPACE.
Client space refers to a coordinate system that originates at the upper
left corner of a Win32 Window's drawable area. This is just inside the
window border and title bar. This client space rectangle, called bounds,
is subsequently converted to screen space with a call to
AdjustWindowRectEx. The problem is found in SDL's handling of the
WM_WINDOWPOSCHANGED message. According to MSDN,
"The WM_WINDOWPOSCHANGED message is sent to a window whose
size, position, or place in the Z order has changed as a
result of a call to the SetWindowPos function or another
window-management function."
I have confirmed that this message is indeed being sent to the SDL window
when the mouse is clicked on the window border, even if the window border
is not dragged.
In video/wincommon/SDL_sysevents.c, on line 464, in response to the
WM_WINDOWPOSCHANGED message, the (potentially) new client rectangle is
obtained. This rectangle is translated into screen coordinates and THEN
assigned to the SDL_windowX and Y variables. Thus screen coordinates are
being assigned to client coordinate variables. Once this is understood,
the solution is apparent: assign SDL_windowX and Y before translating the
rectangle to screen coordinates. This is accomplished by the following
patch.
-Mike_L
author | Sam Lantinga <slouken@libsdl.org> |
---|---|
date | Sun, 29 Jan 2006 08:50:06 +0000 |
parents | 86d0d01290ea |
children | 450721ad5436 |
rev | line source |
---|---|
36
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
1 /* win_ce_semaphore.c |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
2 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
3 Copyright (c) 1998, Johnson M. Hart |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
4 (with corrections 2001 by Rainer Loritz) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
5 Permission is granted for any and all use providing that this |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
6 copyright is properly acknowledged. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
7 There are no assurances of suitability for any use whatsoever. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
8 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
9 WINDOWS CE: There is a collection of Windows CE functions to simulate |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
10 semaphores using only a mutex and an event. As Windows CE events cannot |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
11 be named, these simulated semaphores cannot be named either. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
12 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
13 Implementation notes: |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
14 1. All required internal data structures are allocated on the process's heap. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
15 2. Where appropriate, a new error code is returned (see the header |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
16 file), or, if the error is a Win32 error, that code is unchanged. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
17 3. Notice the new handle type "SYNCHHANDLE" that has handles, counters, |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
18 and other information. This structure will grow as new objects are added |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
19 to this set; some members are specific to only one or two of the objects. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
20 4. Mutexes are used for critical sections. These could be replaced with |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
21 CRITICAL_SECTION objects but then this would give up the time out |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
22 capability. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
23 5. The implementation shows several interesting aspects of synchronization, some |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
24 of which are specific to Win32 and some of which are general. These are pointed |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
25 out in the comments as appropriate. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
26 6. The wait function emulates WaitForSingleObject only. An emulation of |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
27 WaitForMultipleObjects is much harder to implement outside the kernel, |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
28 and it is not clear how to handle a mixture of WCE semaphores and normal |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
29 events and mutexes. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
30 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
31 #include <windows.h> |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
32 #include "win_ce_semaphore.h" |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
33 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
34 static SYNCHHANDLE CleanUp (SYNCHHANDLE hSynch, DWORD Flags); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
35 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
36 SYNCHHANDLE CreateSemaphoreCE ( |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
37 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
38 LPSECURITY_ATTRIBUTES lpSemaphoreAttributes, /* pointer to security attributes */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
39 LONG lInitialCount, /* initial count */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
40 LONG lMaximumCount, /* maximum count */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
41 LPCTSTR lpName ) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
42 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
43 /* Semaphore for use with Windows CE that does not support them directly. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
44 Requires a counter, a mutex to protect the counter, and an |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
45 autoreset event. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
46 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
47 Here are the rules that must always hold between the autoreset event |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
48 and the mutex (any violation of these rules by the CE semaphore functions |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
49 will, in all likelihood, result in a defect): |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
50 1. No thread can set, pulse, or reset the event, |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
51 nor can it access any part of the SYNCHHANDLE structure, |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
52 without first gaining ownership of the mutex. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
53 BUT, a thread can wait on the event without owning the mutex |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
54 (this is clearly necessary or else the event could never be set). |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
55 2. The event is in a signaled state if and only if the current semaphore |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
56 count ("CurCount") is greater than zero. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
57 3. The semaphore count is always >= 0 and <= the maximum count */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
58 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
59 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
60 SYNCHHANDLE hSynch = NULL, result = NULL; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
61 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
62 __try |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
63 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
64 if (lInitialCount > lMaximumCount || lMaximumCount < 0 || lInitialCount < 0) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
65 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
66 /* Bad parameters */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
67 SetLastError (SYNCH_ERROR); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
68 __leave; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
69 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
70 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
71 hSynch = HeapAlloc (GetProcessHeap(), HEAP_ZERO_MEMORY, SYNCH_HANDLE_SIZE); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
72 if (hSynch == NULL) __leave; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
73 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
74 hSynch->MaxCount = lMaximumCount; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
75 hSynch->CurCount = lInitialCount; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
76 hSynch->lpName = lpName; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
77 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
78 hSynch->hMutex = CreateMutex (lpSemaphoreAttributes, FALSE, NULL); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
79 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
80 WaitForSingleObject (hSynch->hMutex, INFINITE); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
81 /* Create the event. It is initially signaled if and only if the |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
82 initial count is > 0 */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
83 hSynch->hEvent = CreateEvent (lpSemaphoreAttributes, FALSE, |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
84 lInitialCount > 0, NULL); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
85 ReleaseMutex (hSynch->hMutex); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
86 hSynch->hSemph = NULL; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
87 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
88 __finally |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
89 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
90 /* Return with the handle, or, if there was any error, return |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
91 a null after closing any open handles and freeing any allocated memory. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
92 result=CleanUp(hSynch, 6 /* An event and a mutex, but no semaphore. */); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
93 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
94 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
95 return result; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
96 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
97 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
98 BOOL ReleaseSemaphoreCE (SYNCHHANDLE hSemCE, LONG cReleaseCount, LPLONG lpPreviousCount) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
99 /* Windows CE equivalent to ReleaseSemaphore. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
100 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
101 BOOL Result = TRUE; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
102 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
103 /* Gain access to the object to assure that the release count |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
104 would not cause the total count to exceed the maximum. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
105 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
106 __try |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
107 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
108 WaitForSingleObject (hSemCE->hMutex, INFINITE); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
109 /* reply only if asked to */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
110 if (lpPreviousCount!=NULL) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
111 *lpPreviousCount = hSemCE->CurCount; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
112 if (hSemCE->CurCount + cReleaseCount > hSemCE->MaxCount || cReleaseCount <= 0) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
113 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
114 SetLastError (SYNCH_ERROR); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
115 Result = FALSE; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
116 __leave; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
117 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
118 hSemCE->CurCount += cReleaseCount; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
119 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
120 /* Set the autoreset event, releasing exactly one waiting thread, now or |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
121 in the future. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
122 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
123 SetEvent (hSemCE->hEvent); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
124 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
125 __finally |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
126 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
127 ReleaseMutex (hSemCE->hMutex); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
128 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
129 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
130 return Result; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
131 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
132 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
133 DWORD WaitForSemaphoreCE (SYNCHHANDLE hSemCE, DWORD dwMilliseconds) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
134 /* Windows CE semaphore equivalent of WaitForSingleObject. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
135 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
136 DWORD WaitResult; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
137 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
138 WaitResult = WaitForSingleObject (hSemCE->hMutex, dwMilliseconds); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
139 if (WaitResult != WAIT_OBJECT_0 && WaitResult != WAIT_ABANDONED_0) return WaitResult; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
140 while (hSemCE->CurCount <= 0) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
141 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
142 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
143 /* The count is 0, and the thread must wait on the event (which, by |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
144 the rules, is currently reset) for semaphore resources to become |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
145 available. First, of course, the mutex must be released so that another |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
146 thread will be capable of setting the event. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
147 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
148 ReleaseMutex (hSemCE->hMutex); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
149 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
150 /* Wait for the event to be signaled, indicating a semaphore state change. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
151 The event is autoreset and signaled with a SetEvent (not PulseEvent) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
152 so exactly one waiting thread (whether or not there is currently |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
153 a waiting thread) is released as a result of the SetEvent. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
154 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
155 WaitResult = WaitForSingleObject (hSemCE->hEvent, dwMilliseconds); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
156 if (WaitResult != WAIT_OBJECT_0) return WaitResult; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
157 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
158 /* This is where the properties of setting of an autoreset event is critical |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
159 to assure that, even if the semaphore state changes between the |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
160 preceding Wait and the next, and even if NO threads are waiting |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
161 on the event at the time of the SetEvent, at least one thread |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
162 will be released. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
163 Pulsing a manual reset event would appear to work, but it would have |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
164 a defect which could appear if the semaphore state changed between |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
165 the two waits. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
166 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
167 WaitResult = WaitForSingleObject (hSemCE->hMutex, dwMilliseconds); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
168 if (WaitResult != WAIT_OBJECT_0 && WaitResult != WAIT_ABANDONED_0) return WaitResult; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
169 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
170 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
171 /* The count is not zero and this thread owns the mutex. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
172 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
173 hSemCE->CurCount--; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
174 /* The event is now unsignaled, BUT, the semaphore count may not be |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
175 zero, in which case the event should be signaled again |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
176 before releasing the mutex. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
177 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
178 if (hSemCE->CurCount > 0) SetEvent (hSemCE->hEvent); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
179 ReleaseMutex (hSemCE->hMutex); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
180 return WaitResult; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
181 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
182 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
183 BOOL CloseSynchHandle (SYNCHHANDLE hSynch) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
184 /* Close a synchronization handle. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
185 Improvement: Test for a valid handle before dereferencing the handle. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
186 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
187 BOOL Result = TRUE; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
188 if (hSynch->hEvent != NULL) Result = Result && CloseHandle (hSynch->hEvent); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
189 if (hSynch->hMutex != NULL) Result = Result && CloseHandle (hSynch->hMutex); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
190 if (hSynch->hSemph != NULL) Result = Result && CloseHandle (hSynch->hSemph); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
191 HeapFree (GetProcessHeap (), 0, hSynch); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
192 return (Result); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
193 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
194 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
195 static SYNCHHANDLE CleanUp (SYNCHHANDLE hSynch, DWORD Flags) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
196 { /* Prepare to return from a create of a synchronization handle. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
197 If there was any failure, free any allocated resources. |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
198 "Flags" indicates which Win32 objects are required in the |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
199 synchronization handle. */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
200 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
201 BOOL ok = TRUE; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
202 |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
203 if (hSynch == NULL) return NULL; |
1251
86d0d01290ea
Updated Windows CE/PocketPC support...adds GAPI driver, landscape mode,
Ryan C. Gordon <icculus@icculus.org>
parents:
36
diff
changeset
|
204 if ((Flags & 4) == 1 && (hSynch->hEvent == NULL)) ok = FALSE; |
86d0d01290ea
Updated Windows CE/PocketPC support...adds GAPI driver, landscape mode,
Ryan C. Gordon <icculus@icculus.org>
parents:
36
diff
changeset
|
205 if ((Flags & 2) == 1 && (hSynch->hMutex == NULL)) ok = FALSE; |
86d0d01290ea
Updated Windows CE/PocketPC support...adds GAPI driver, landscape mode,
Ryan C. Gordon <icculus@icculus.org>
parents:
36
diff
changeset
|
206 if ((Flags & 1) == 1 && (hSynch->hEvent == NULL)) ok = FALSE; |
36
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
207 if (!ok) |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
208 { |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
209 CloseSynchHandle (hSynch); |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
210 return NULL; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
211 } |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
212 /* Everything worked */ |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
213 return hSynch; |
13ee9f4834ea
Windows CE patches contributed by Rainer Loritz
Sam Lantinga <slouken@lokigames.com>
parents:
diff
changeset
|
214 } |