aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPaul Gilbert2012-06-09 17:14:21 +1000
committerPaul Gilbert2012-06-09 17:14:21 +1000
commit26bb3d67329112e0bd49013628cdf4d8f4473766 (patch)
tree83b93d897e08116e4df02b6f1e65140de1e0880f
parenta50b1f32c1de667cd2d73535b07e62b000cf4483 (diff)
downloadscummvm-rg350-26bb3d67329112e0bd49013628cdf4d8f4473766.tar.gz
scummvm-rg350-26bb3d67329112e0bd49013628cdf4d8f4473766.tar.bz2
scummvm-rg350-26bb3d67329112e0bd49013628cdf4d8f4473766.zip
COMMON: Changed pulseEvent to allow calling processes to finish executing first
-rw-r--r--common/coroutines.cpp56
-rw-r--r--common/coroutines.h1
2 files changed, 17 insertions, 40 deletions
diff --git a/common/coroutines.cpp b/common/coroutines.cpp
index 4a45f2ec23..9ef7c73e38 100644
--- a/common/coroutines.cpp
+++ b/common/coroutines.cpp
@@ -259,6 +259,15 @@ void CoroutineScheduler::schedule() {
pProc = pNext;
}
+
+ // Disable any events that were pulsed
+ Common::List<EVENT *>::iterator i;
+ for (i = _events.begin(); i != _events.end(); ++i) {
+ EVENT *evt = *i;
+ if (evt->pulsing) {
+ evt->pulsing = evt->signalled = false;
+ }
+ }
}
/**
@@ -787,6 +796,7 @@ uint32 CoroutineScheduler::createEvent(bool bManualReset, bool bInitialState) {
evt->pid = ++pidCounter;
evt->manualReset = bManualReset;
evt->signalled = bInitialState;
+ evt->pulsing = false;
_events.push_back(evt);
return evt->pid;
@@ -836,48 +846,14 @@ void CoroutineScheduler::pulseEvent(uint32 pidEvent) {
if (!evt)
return;
- // Set the event as true
+ // Set the event as signalled and pulsing
evt->signalled = true;
-
- // start dispatching active process list for any processes that are currently waiting
- PROCESS *pOriginal = pCurrent;
- PROCESS *pNext;
- PROCESS *pProc = active->pNext;
- while (pProc != NULL) {
- pNext = pProc->pNext;
-
- // Only call processes that are currently waiting (either in waitForSingleObject or
- // waitForMultipleObjects) for the given event Pid
- for (int i = 0; i < CORO_MAX_PID_WAITING; ++i) {
- if (pProc->pidWaiting[i] == pidEvent) {
- // Dispatch the process
- pCurrent = pProc;
- pProc->coroAddr(pProc->state, pProc->param);
-
- if (!pProc->state || pProc->state->_sleep <= 0) {
- // Coroutine finished
- pCurrent = pCurrent->pPrevious;
- killProcess(pProc);
- } else {
- pProc->sleepTime = pProc->state->_sleep;
- }
-
- // pCurrent may have been changed
- pNext = pCurrent->pNext;
- pCurrent = NULL;
-
- break;
- }
- }
-
- pProc = pNext;
- }
-
- // Restore the original current process (if one was active)
- pCurrent = pOriginal;
+ evt->pulsing = true;
- // Reset the event back to non-signalled
- evt->signalled = false;
+ // If there's an active process, and it's not the first in the queue, then reschedule all
+ // the other prcoesses in the queue to run again this frame
+ if (pCurrent && pCurrent != active->pNext)
+ rescheduleAll();
}
diff --git a/common/coroutines.h b/common/coroutines.h
index 6df843887c..86e284d2b1 100644
--- a/common/coroutines.h
+++ b/common/coroutines.h
@@ -306,6 +306,7 @@ struct EVENT {
uint32 pid;
bool manualReset;
bool signalled;
+ bool pulsing;
};