fix handling of SDL_EventQ.active - SDL_EventQ.active is a bool variable -> do not use SDL_AtomicGet/Set, it does not help in any way - protect SDL_EventQ.active with SDL_EventQ.lock - set SDL_EventQ.active to FALSE by default
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120
diff --git a/src/events/SDL_events.c b/src/events/SDL_events.c
index 00a4053..52b72cd 100644
--- a/src/events/SDL_events.c
+++ b/src/events/SDL_events.c
@@ -86,7 +86,7 @@ typedef struct _SDL_SysWMEntry
static struct
{
SDL_mutex *lock;
- SDL_atomic_t active;
+ SDL_bool active;
SDL_atomic_t count;
int max_events_seen;
SDL_EventEntry *head;
@@ -94,7 +94,7 @@ static struct
SDL_EventEntry *free;
SDL_SysWMEntry *wmmsg_used;
SDL_SysWMEntry *wmmsg_free;
-} SDL_EventQ = { NULL, { 1 }, { 0 }, 0, NULL, NULL, NULL, NULL, NULL };
+} SDL_EventQ = { NULL, SDL_FALSE, { 0 }, 0, NULL, NULL, NULL, NULL, NULL };
#if !SDL_JOYSTICK_DISABLED
@@ -474,7 +474,7 @@ SDL_StopEventLoop(void)
SDL_LockMutex(SDL_EventQ.lock);
}
- SDL_AtomicSet(&SDL_EventQ.active, 0);
+ SDL_EventQ.active = SDL_FALSE;
if (report && SDL_atoi(report)) {
SDL_Log("SDL EVENT QUEUE: Maximum events in-flight: %d\n",
@@ -554,10 +554,12 @@ SDL_StartEventLoop(void)
return -1;
}
}
+ SDL_LockMutex(SDL_EventQ.lock);
if (!SDL_event_watchers_lock) {
SDL_event_watchers_lock = SDL_CreateMutex();
if (SDL_event_watchers_lock == NULL) {
+ SDL_UnlockMutex(SDL_EventQ.lock);
return -1;
}
}
@@ -572,8 +574,10 @@ SDL_StartEventLoop(void)
SDL_EventState(SDL_DROPTEXT, SDL_DISABLE);
#endif
- SDL_AtomicSet(&SDL_EventQ.active, 1);
-
+ SDL_EventQ.active = SDL_TRUE;
+ if (SDL_EventQ.lock) {
+ SDL_UnlockMutex(SDL_EventQ.lock);
+ }
return 0;
}
@@ -692,17 +696,20 @@ SDL_PeepEventsInternal(SDL_Event * events, int numevents, SDL_eventaction action
{
int i, used, sentinels_expected = 0;
- /* Don't look after we've quit */
- if (!SDL_AtomicGet(&SDL_EventQ.active)) {
- /* We get a few spurious events at shutdown, so don't warn then */
- if (action == SDL_GETEVENT) {
- SDL_SetError("The event system has been shut down");
- }
- return (-1);
- }
/* Lock the event queue */
used = 0;
if (!SDL_EventQ.lock || SDL_LockMutex(SDL_EventQ.lock) == 0) {
+ /* Don't look after we've quit */
+ if (!SDL_EventQ.active) {
+ if (SDL_EventQ.lock) {
+ SDL_UnlockMutex(SDL_EventQ.lock);
+ }
+ /* We get a few spurious events at shutdown, so don't warn then */
+ if (action == SDL_GETEVENT) {
+ SDL_SetError("The event system has been shut down");
+ }
+ return (-1);
+ }
if (action == SDL_ADDEVENT) {
for (i = 0; i < numevents; ++i) {
used += SDL_AddEvent(&events[i]);
@@ -810,15 +817,12 @@ SDL_FlushEvent(Uint32 type)
void
SDL_FlushEvents(Uint32 minType, Uint32 maxType)
{
+ SDL_EventEntry *entry, *next;
+ Uint32 type;
/* !!! FIXME: we need to manually SDL_free() the strings in TEXTINPUT and
drag'n'drop events if we're flushing them without passing them to the
app, but I don't know if this is the right place to do that. */
- /* Don't look after we've quit */
- if (!SDL_AtomicGet(&SDL_EventQ.active)) {
- return;
- }
-
/* Make sure the events are current */
#if 0
/* Actually, we can't do this since we might be flushing while processing
@@ -829,8 +833,13 @@ SDL_FlushEvents(Uint32 minType, Uint32 maxType)
/* Lock the event queue */
if (!SDL_EventQ.lock || SDL_LockMutex(SDL_EventQ.lock) == 0) {
- SDL_EventEntry *entry, *next;
- Uint32 type;
+ /* Don't look after we've quit */
+ if (!SDL_EventQ.active) {
+ if (SDL_EventQ.lock) {
+ SDL_UnlockMutex(SDL_EventQ.lock);
+ }
+ return;
+ }
for (entry = SDL_EventQ.head; entry; entry = next) {
next = entry->next;
type = entry->event.type;