ViewVC Help
View File | Revision Log | Show Annotations | Revision Graph | Root Listing
root/cebix/BasiliskII/src/Windows/timer_windows.cpp
(Generate patch)

Comparing BasiliskII/src/Windows/timer_windows.cpp (file contents):
Revision 1.3 by gbeauche, 2004-12-03T22:05:36Z vs.
Revision 1.6 by gbeauche, 2006-05-01T06:12:50Z

# Line 1 | Line 1
1   /*
2   *  timer_windows.cpp - Time Manager emulation, Windows specific stuff
3   *
4 < *  Basilisk II (C) 1997-2004 Christian Bauer
4 > *  Basilisk II (C) 1997-2005 Christian Bauer
5   *
6   *  This program is free software; you can redistribute it and/or modify
7   *  it under the terms of the GNU General Public License as published by
# Line 36 | Line 36
36   #define USECS2TICKS(USECS) (((uint64)(USECS) * frequency) / 1000000)
37   #define TICKS2USECS(TICKS) (((uint64)(TICKS) * 1000000) / frequency)
38  
39 + // From main_windows.cpp
40 + extern HANDLE emul_thread;
41 +
42   // Global variables
43   static uint32 frequency;                                // CPU frequency in Hz (< 4 GHz)
44   static tm_time_t mac_boot_ticks;
# Line 195 | Line 198 | void Delay_usec(uint32 usec)
198          // millisecond resolution anyway
199          Sleep(usec / 1000);
200   }
201 +
202 +
203 + /*
204 + *  Suspend emulator thread, virtual CPU in idle mode
205 + */
206 +
207 + struct idle_sentinel {
208 +        idle_sentinel();
209 +        ~idle_sentinel();
210 + };
211 + static idle_sentinel idle_sentinel;
212 +
213 + static int idle_sem_ok = -1;
214 + static HANDLE idle_sem = NULL;
215 +
216 + static HANDLE idle_lock = NULL;
217 + #define LOCK_IDLE WaitForSingleObject(idle_lock, INFINITE)
218 + #define UNLOCK_IDLE ReleaseMutex(idle_lock)
219 +
220 + idle_sentinel::idle_sentinel()
221 + {
222 +        LOCK_IDLE;
223 +        idle_sem_ok = 1;
224 +        if ((idle_sem = CreateSemaphore(0, 0, 1, NULL)) == NULL)
225 +                idle_sem_ok = 0;
226 +        if ((idle_lock = CreateMutex(NULL, FALSE, NULL)) == NULL)
227 +                idle_sem_ok = 0;
228 +        UNLOCK_IDLE;
229 + }
230 +
231 + idle_sentinel::~idle_sentinel()
232 + {
233 +        if (idle_lock) {
234 +                ReleaseMutex(idle_lock);
235 +                CloseHandle(idle_lock);
236 +        }
237 +        if (idle_sem) {
238 +                ReleaseSemaphore(idle_sem, 1, NULL);
239 +                CloseHandle(idle_sem);
240 +        }
241 + }
242 +
243 + void idle_wait(void)
244 + {
245 +        LOCK_IDLE;
246 +        if (idle_sem_ok > 0) {
247 +                idle_sem_ok++;
248 +                UNLOCK_IDLE;
249 +                WaitForSingleObject(idle_sem, INFINITE);
250 +                return;
251 +        }
252 +        UNLOCK_IDLE;
253 +
254 +        // Fallback: sleep 10 ms (this should not happen though)
255 +        Delay_usec(10000);
256 + }
257 +
258 +
259 + /*
260 + *  Resume execution of emulator thread, events just arrived
261 + */
262 +
263 + void idle_resume(void)
264 + {
265 +        LOCK_IDLE;
266 +        if (idle_sem_ok > 1) {
267 +                idle_sem_ok--;
268 +                UNLOCK_IDLE;
269 +                ReleaseSemaphore(idle_sem, 1, NULL);
270 +                return;
271 +        }
272 +        UNLOCK_IDLE;
273 + }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines