|
|
1.1 root 1: /*
2: * UAE - The Un*x Amiga Emulator
3: *
4: * Events
1.1.1.4 root 5: * These are best for low-frequency events. Having too many of them,
6: * or using them for events that occur too frequently, can cause massive
7: * slowdown.
1.1.1.3 root 8: *
1.1.1.4 root 9: * Copyright 1995-1998 Bernd Schmidt
1.1 root 10: */
11:
1.1.1.4 root 12: #include "machdep/rpt.h"
1.1.1.9 root 13:
1.1.1.4 root 14: extern frame_time_t vsynctime, vsyncmintime;
15: extern void reset_frame_rate_hack (void);
16: extern int rpt_available;
17:
1.1.1.11! root 18: extern void compute_vsynctime (void);
! 19:
1.1.1.9 root 20: extern unsigned long currcycle, nextevent, is_lastline;
21: extern unsigned long sample_evtime;
1.1 root 22: typedef void (*evfunc)(void);
23:
24: struct ev
25: {
26: int active;
27: unsigned long int evtime, oldcycles;
28: evfunc handler;
29: };
30:
1.1.1.3 root 31: enum {
1.1.1.9 root 32: ev_hsync, ev_copper, ev_audio, ev_cia, ev_blitter, ev_disk,
1.1 root 33: ev_max
34: };
35:
36: extern struct ev eventtab[ev_max];
37:
1.1.1.5 root 38: STATIC_INLINE void events_schedule (void)
1.1 root 39: {
40: int i;
1.1.1.3 root 41:
1.1 root 42: unsigned long int mintime = ~0L;
1.1.1.9 root 43: for (i = 0; i < ev_max; i++) {
1.1.1.3 root 44: if (eventtab[i].active) {
1.1.1.9 root 45: unsigned long int eventtime = eventtab[i].evtime - currcycle;
1.1 root 46: if (eventtime < mintime)
1.1.1.3 root 47: mintime = eventtime;
1.1 root 48: }
49: }
1.1.1.9 root 50: nextevent = currcycle + mintime;
1.1 root 51: }
52:
1.1.1.5 root 53: STATIC_INLINE void do_cycles_slow (unsigned long cycles_to_add)
1.1 root 54: {
1.1.1.9 root 55: if (is_lastline && eventtab[ev_hsync].evtime - currcycle <= cycles_to_add
1.1.1.3 root 56: && (long int)(read_processor_time () - vsyncmintime) < 0)
57: return;
1.1.1.4 root 58:
1.1.1.9 root 59: while ((nextevent - currcycle) <= cycles_to_add) {
60: int i;
61: cycles_to_add -= (nextevent - currcycle);
62: currcycle = nextevent;
63:
64: for (i = 0; i < ev_max; i++) {
65: if (eventtab[i].active && eventtab[i].evtime == currcycle) {
66: (*eventtab[i].handler)();
1.1 root 67: }
68: }
1.1.1.9 root 69: events_schedule();
1.1 root 70: }
1.1.1.9 root 71: currcycle += cycles_to_add;
1.1 root 72: }
73:
1.1.1.5 root 74: STATIC_INLINE void do_cycles_fast (void)
1.1 root 75: {
1.1.1.9 root 76: if (is_lastline && eventtab[ev_hsync].evtime - currcycle <= 1
1.1.1.3 root 77: && (long int)(read_processor_time () - vsyncmintime) < 0)
78: return;
1.1.1.4 root 79:
1.1.1.9 root 80: currcycle++;
81: if (nextevent == currcycle) {
1.1 root 82: int i;
1.1.1.3 root 83:
1.1.1.4 root 84: for (i = 0; i < ev_max; i++) {
1.1.1.9 root 85: if (eventtab[i].active && eventtab[i].evtime == currcycle) {
1.1.1.4 root 86: (*eventtab[i].handler) ();
1.1 root 87: }
88: }
89: events_schedule();
90: }
91:
92: }
93:
1.1.1.10 root 94: /* This is a special-case function. Normally, all events should lie in the
95: future; they should only ever be active at the current cycle during
96: do_cycles. However, a snapshot is saved during do_cycles, and so when
97: restoring it, we may have other events pending. */
98: STATIC_INLINE void handle_active_events (void)
99: {
100: int i;
101: for (i = 0; i < ev_max; i++) {
102: if (eventtab[i].active && eventtab[i].evtime == currcycle) {
103: (*eventtab[i].handler)();
104: }
105: }
106: }
107:
1.1.1.9 root 108: STATIC_INLINE unsigned long get_cycles (void)
109: {
110: return currcycle;
111: }
112:
1.1.1.10 root 113: extern void init_eventtab (void);
114:
1.1.1.3 root 115: #if /* M68K_SPEED == 1 */ 0
1.1 root 116: #define do_cycles do_cycles_fast
117: #else
118: #define do_cycles do_cycles_slow
119: #endif
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.