glutTimerFunc cleanup
authorDaniel Borca <dborca@users.sourceforge.net>
Mon, 26 Jan 2004 10:41:39 +0000 (10:41 +0000)
committerDaniel Borca <dborca@users.sourceforge.net>
Mon, 26 Jan 2004 10:41:39 +0000 (10:41 +0000)
src/glut/dos/Makefile.DJ
src/glut/dos/PC_HW/pc_timer.c
src/glut/dos/callback.c
src/glut/dos/glutint.h

index 4586a0ba6991067c2d82823d028aaa8f37354238..b7c770715de3897418e882726c636724fcf3e8bb 100644 (file)
@@ -20,7 +20,7 @@
 # AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
 # CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 
-# DOS/DJGPP glut makefile v1.4 for Mesa
+# DOS/DJGPP glut makefile v1.5 for Mesa
 #
 #  Copyright (C) 2002 - Borca Daniel
 #  Email : dborca@users.sourceforge.net
@@ -34,7 +34,9 @@
 #      CFLAGS
 #
 #      MKGLUT          absolute path to original GLUT.
-#                      default = $(TOP)/src-glut
+#                      default = $(TOP)/src/glut/glx
+#      GLIDE           path to Glide3 SDK; used to resolve DXEs.
+#                      default = $(TOP)/glide3
 #
 #    Targets:
 #      all:            build GLUT
@@ -46,7 +48,7 @@
 .PHONY: all clean
 
 TOP = ../../..
-GLIDE ?= $(TOP)/include/glide3
+GLIDE ?= $(TOP)/glide3
 MKGLUT ?= $(TOP)/src/glut/glx
 LIBDIR = $(TOP)/lib
 GLUT_LIB = libglut.a
index f11917db1aa5620409fc96b6e68aa780dbdd7ee2..530ed72a49373ad40ae43e3226ff8c46f405425f 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * PC/HW routine collection v1.4 for DOS/DJGPP
+ * PC/HW routine collection v1.5 for DOS/DJGPP
  *
  *  Copyright (C) 2002 - Borca Daniel
  *  Email : dborca@yahoo.com
@@ -93,106 +93,6 @@ void pc_remove_timer (void)
 
 
 
-/* Desc: install timer engine
- *
- * In  : -
- * Out : 0 for success
- *
- * Note: initial frequency is 18.2 Hz
- */
-static int install_timer (void)
-{
- if (timer_installed || pc_install_irq(TIMER_IRQ, timer)) {
-    return -1;
- } else {
-    memset(timer_func, 0, sizeof(timer_func));
-    LOCKDATA(timer_func);
-    LOCKDATA(timer_main);
-    LOCKFUNC(timer);
-
-    timer_main.counter = 0x10000;
-
-    DISABLE();
-    outportb(0x43, 0x34);
-    outportb(0x40, 0);
-    outportb(0x40, 0);
-    timer_main.clock_ticks = 0;
-    ENABLE();
-
-    pc_atexit(pc_remove_timer);
-    timer_installed = TRUE;
-    return 0;
- }
-}
-
-
-
-/* Desc: install timerfunc
- *
- * In  : callback function, opaque pointer to be passed to callee, freq (Hz)
- * Out : timerfunc id (0 .. MAX_TIMERS-1)
- *
- * Note: returns -1 if error
- */
-int pc_install_int (PFUNC func, void *parm, unsigned int freq)
-{
- int i;
- TIMER *t = NULL;
-
- /* ensure the timer engine is set up */
- if (!timer_installed) {
-    if (install_timer()) {
-       return -1;
-    }
- }
-
- /* find an empty slot */
- for (i = 0; i < MAX_TIMERS; i++) {
-     if (!timer_func[i].func) {
-        t = &timer_func[i];
-        break;
-     }
- }
- if (t == NULL) {
-    return -1;
- }
-
- DISABLE();
-
- t->func = func;
- t->parm = parm;
- t->freq = freq;
- t->clock_ticks = 0;
-
- /* update main timer / sons to match highest frequency */
- if (freq > timer_main.freq) {
-    unsigned int new_counter = PIT_FREQ / freq;
-
-    for (i = 0; i < MAX_TIMERS; i++) {
-        if (timer_func[i].func) {
-           ADJUST(timer_func[i], freq);
-        }
-    }
-
-    outportb(0x43, 0x34);
-    outportb(0x40, (unsigned char)new_counter);
-    outportb(0x40, (unsigned char)(new_counter>>8));
-    timer_main.clock_ticks = 0;
-    timer_main.counter = new_counter;
-    timer_main.freq = freq;
- } else {
-    /* t == &timer_func[i] */
-    ADJUST(timer_func[i], timer_main.freq);
- }
-
- ENABLE();
-
- return t - timer_func;
-}
-
-
-
 /* Desc: remove timerfunc
  *
  * In  : timerfunc id
@@ -255,7 +155,7 @@ int pc_remove_int (int fid)
  }
  
  return 0;
-}
+} ENDOFUNC(pc_remove_int)
 
 
 
@@ -320,4 +220,108 @@ int pc_adjust_int (int fid, unsigned int freq)
  ENABLE();
 
  return 0;
+} ENDOFUNC(pc_adjust_int)
+
+
+
+/* Desc: install timer engine
+ *
+ * In  : -
+ * Out : 0 for success
+ *
+ * Note: initial frequency is 18.2 Hz
+ */
+static int install_timer (void)
+{
+ if (timer_installed || pc_install_irq(TIMER_IRQ, timer)) {
+    return -1;
+ } else {
+    memset(timer_func, 0, sizeof(timer_func));
+    LOCKDATA(timer_func);
+    LOCKDATA(timer_main);
+    LOCKFUNC(timer);
+    LOCKFUNC(pc_adjust_int);
+    LOCKFUNC(pc_remove_int);
+
+    timer_main.counter = 0x10000;
+
+    DISABLE();
+    outportb(0x43, 0x34);
+    outportb(0x40, 0);
+    outportb(0x40, 0);
+    timer_main.clock_ticks = 0;
+    ENABLE();
+
+    pc_atexit(pc_remove_timer);
+    timer_installed = TRUE;
+    return 0;
+ }
+}
+
+
+
+/* Desc: install timerfunc
+ *
+ * In  : callback function, opaque pointer to be passed to callee, freq (Hz)
+ * Out : timerfunc id (0 .. MAX_TIMERS-1)
+ *
+ * Note: returns -1 if error
+ */
+int pc_install_int (PFUNC func, void *parm, unsigned int freq)
+{
+ int i;
+ TIMER *t = NULL;
+
+ /* ensure the timer engine is set up */
+ if (!timer_installed) {
+    if (install_timer()) {
+       return -1;
+    }
+ }
+
+ /* find an empty slot */
+ for (i = 0; i < MAX_TIMERS; i++) {
+     if (!timer_func[i].func) {
+        t = &timer_func[i];
+        break;
+     }
+ }
+ if (t == NULL) {
+    return -1;
+ }
+
+ DISABLE();
+
+ t->func = func;
+ t->parm = parm;
+ t->freq = freq;
+ t->clock_ticks = 0;
+
+ /* update main timer / sons to match highest frequency */
+ if (freq > timer_main.freq) {
+    unsigned int new_counter = PIT_FREQ / freq;
+
+    for (i = 0; i < MAX_TIMERS; i++) {
+        if (timer_func[i].func) {
+           ADJUST(timer_func[i], freq);
+        }
+    }
+
+    outportb(0x43, 0x34);
+    outportb(0x40, (unsigned char)new_counter);
+    outportb(0x40, (unsigned char)(new_counter>>8));
+    timer_main.clock_ticks = 0;
+    timer_main.counter = new_counter;
+    timer_main.freq = freq;
+ } else {
+    /* t == &timer_func[i] */
+    ADJUST(timer_func[i], timer_main.freq);
+ }
+
+ i = t - timer_func;
+
+ ENABLE();
+
+ return i;
 }
index 174cbdda99648f4f9631fce28d71fa895ca1abfe..773dfb275893f67248b4f730e1826dc64b110791 100644 (file)
@@ -19,7 +19,7 @@
  */
 
 /*
- * DOS/DJGPP glut driver v1.4 for Mesa
+ * DOS/DJGPP glut driver v1.5 for Mesa
  *
  *  Copyright (C) 2002 - Borca Daniel
  *  Email : dborca@yahoo.com
@@ -38,8 +38,6 @@ typedef struct {
         int fid;            /* func-id as returned from PCHW */
 } GLUTSShotCB;
 
-static GLboolean g_sscb_semaphore;
-
 GLUTidleCB g_idle_func = NULL;
 
 
@@ -47,11 +45,12 @@ GLUTidleCB g_idle_func = NULL;
 static void g_single_shot_callback (void *opaque)
 {
  GLUTSShotCB *cb = (GLUTSShotCB *)opaque;
- while (g_sscb_semaphore) {
- }
  if (!--cb->ttl) {
     cb->func(cb->value);
     pc_remove_int(cb->fid);
+    /* We won't be needing this slot anymore, so free it. This operation
+     * must be the last thing, and must be atomic, to mutex `glutTimerFunc'
+     */
     cb->func = NULL;
  }
 } ENDOFUNC(g_single_shot_callback)
@@ -139,7 +138,6 @@ void APIENTRY glutTimerFunc (unsigned int millis, GLUTtimerCB func, int value)
  if (virgin) {
     virgin = GL_FALSE;
     LOCKDATA(g_sscb);
-    LOCKDATA(g_sscb_semaphore);
     LOCKFUNC(g_single_shot_callback);
     /* we should lock the callee also... */
  }
@@ -153,20 +151,27 @@ void APIENTRY glutTimerFunc (unsigned int millis, GLUTtimerCB func, int value)
        freq = 1000 / millis;
        ttl = 1;
     }
-    g_sscb_semaphore++;
     for (i = 0; i < MAX_SSHOT_CB; i++) {
         if (g_sscb[i].func == NULL) {
-           int fid = pc_install_int((PFUNC)func, &g_sscb[i], freq);
-           if (fid >= 0) {
-              g_sscb[i].func = func;
-              g_sscb[i].value = value;
-              g_sscb[i].ttl = ttl;
-              g_sscb[i].fid = fid;
+           /* We will be needing this slot, so alloc it. This operation
+            * must be the first thing, and must be atomic, to mutex callbacks!
+            */
+           g_sscb[i].func = func;
+           g_sscb[i].value = value;
+           g_sscb[i].ttl = ttl;
+           /* There is a very small gap here: `pc_install_int' enables
+            * interrupts just before returning FID value (which will be
+            * used inside callback). The critical gap is 1 millisecond
+            * - which I'm sure we won't overrun...
+            */
+           g_sscb[i].fid = pc_install_int((PFUNC)func, &g_sscb[i], freq);
+           if (g_sscb[i].fid < 0) {
+              /* Interrupt could not be set! Release the slot back */
+              g_sscb[i].func = NULL;
            }
            break;
         }
     }
-    g_sscb_semaphore--;
  }
 }
 
index 2cd0dde1b87eeb3210572a26dfc9fbf52db76331..12750041fe14ea5aa9972c229629160dc46da340 100644 (file)
@@ -19,7 +19,7 @@
  */
 
 /*
- * DOS/DJGPP glut driver v1.5 for Mesa
+ * DOS/DJGPP glut driver v1.6 for Mesa
  *
  *  Copyright (C) 2002 - Borca Daniel
  *  Email : dborca@users.sourceforge.net
@@ -146,7 +146,7 @@ extern void *__glutFont(void *font);
 
 #define MAX_WINDOWS 2
 
-#define MAX_SSHOT_CB 10
+#define MAX_SSHOT_CB 8
 
 #define RESERVED_COLORS 0