cell: checkpoint: more work in emit_function_call()
[mesa.git] / src / glut / fbdev / fbdev.c
index ce6419816dde1f7c5c9c50c68fb5a441134d0ed0..80237f5bc750745e5d820d9adb282870bef596e2 100644 (file)
@@ -74,6 +74,7 @@ int Redisplay;
 int Visible;
 int VisibleSwitch;
 int Active;
+static int Resized;
 /* we have to poll to see if we are visible
    on a framebuffer that is not active */
 int VisiblePoll;
@@ -127,8 +128,10 @@ static void Cleanup(void)
         fprintf(stderr, "ioctl(FBIOPUT_VSCREENINFO failed): %s\n",
                 strerror(errno));
 
-      munmap(FrameBuffer, FixedInfo.smem_len);
+      if(FrameBuffer)
+         munmap(FrameBuffer, FixedInfo.smem_len);
       close(FrameBufferFD);
+
    }
 
    /* free allocated back buffer */
@@ -170,6 +173,9 @@ void glutInit (int *argcp, char **argv)
    int RequiredWidth = 0, RequiredHeight;
    char *fbdev;
 
+   stack_t stack;
+   struct sigaction sa;
+
    /* parse out args */
    for (i = 1; i < *argcp;) {
       if (!strcmp(argv[i], "-geometry")) {
@@ -236,7 +242,19 @@ void glutInit (int *argcp, char **argv)
    gettimeofday(&StartTime, 0);
    atexit(Cleanup);
 
-   signal(SIGSEGV, CrashHandler);
+   /* set up SIGSEGV to use alternate stack */
+   stack.ss_flags = 0;
+   stack.ss_size = SIGSTKSZ;
+   if(!(stack.ss_sp = malloc(SIGSTKSZ)))
+      sprintf(exiterror, "Failed to allocate alternate stack for SIGSEGV!\n");
+
+   sigaltstack(&stack, NULL);
+
+   sa.sa_handler = CrashHandler;
+   sa.sa_flags = SA_ONSTACK;
+   sigemptyset(&sa.sa_mask);
+   sigaction(SIGSEGV, &sa, NULL);
+
    signal(SIGINT, CrashHandler);
    signal(SIGTERM, CrashHandler);
    signal(SIGABRT, CrashHandler);
@@ -424,6 +442,8 @@ static void ProcessTimers(void)
 
 void glutMainLoop(void)
 {
+   int idleiters;
+
    if(ReshapeFunc)
       ReshapeFunc(VarInfo.xres, VarInfo.yres);
 
@@ -440,8 +460,6 @@ void glutMainLoop(void)
       else
         if(VisiblePoll)
            TestVisible();
-        else
-           usleep(1);
 
       if(IdleFunc)
         IdleFunc();
@@ -452,17 +470,48 @@ void glutMainLoop(void)
            VisibilityFunc(Visible ? GLUT_VISIBLE : GLUT_NOT_VISIBLE);
       }
 
+      if(Resized) {
+         SetVideoMode();
+         CreateBuffer();
+
+         if(!glFBDevMakeCurrent( Context, Buffer, Buffer )) {
+            sprintf(exiterror, "Failure to Make Current\n");
+            exit(0);
+         }
+
+         InitializeMenus();
+
+         if(ReshapeFunc)
+            ReshapeFunc(VarInfo.xres, VarInfo.yres);
+
+         Redisplay = 1;
+         Resized = 0;
+      }
+
       if(Visible && Redisplay) {
         Redisplay = 0;
-        if(MouseEnabled)
-           EraseCursor();
+         EraseCursor();
         DisplayFunc();
         if(!(DisplayMode & GLUT_DOUBLE)) {
            if(ActiveMenu)
               DrawMenus();
-           if(MouseEnabled)
-              DrawCursor();
+            DrawCursor();
         }
+         idleiters = 0;
+      } else {
+         /* we sleep if not receiving redisplays, and
+            the main loop is running faster than 2khz */
+
+         static int lasttime;
+         int time = glutGet(GLUT_ELAPSED_TIME);
+         if(time > lasttime) {
+            if(idleiters >= 2)
+               usleep(100);
+
+            idleiters = 0;
+            lasttime = time;
+         }
+         idleiters++;         
       }
    }
 }
@@ -536,17 +585,16 @@ int ParseFBModes(int minw, int maxw, int minh, int maxh, int minf, int maxf)
    return 0;
 }
 
-/* ---------- Window Management ----------*/
 void SetVideoMode(void)
 {
    /* set new variable screen info */
    if (ioctl(FrameBufferFD, FBIOPUT_VSCREENINFO, &VarInfo)) {
-      sprintf(exiterror, "ioctl(FBIOPUT_VSCREENINFO failed): %s\n",
-             strerror(errno));
+      sprintf(exiterror, "FBIOPUT_VSCREENINFO failed: %s\n", strerror(errno));
+      strcat(exiterror, "Perhaps the device does not support the selected mode\n");
       exit(0);
    }
 
-   /* reload the screen info to update offsets */
+   /* reload the screen info to update rgb bits */
    if (ioctl(FrameBufferFD, FBIOGET_VSCREENINFO, &VarInfo)) {
       sprintf(exiterror, "error: ioctl(FBIOGET_VSCREENINFO) failed: %s\n",
              strerror(errno));
@@ -574,7 +622,7 @@ void SetVideoMode(void)
    LoadColorMap();
 }
 
-void CreateBuffer()
+void CreateBuffer(void)
 {
    int size = VarInfo.xres_virtual * VarInfo.yres_virtual
                               * VarInfo.bits_per_pixel / 8;
@@ -673,20 +721,6 @@ void CreateVisual(void)
    }
 }
 
-static void ResizeVisual(void)
-{ 
-   if(!glFBDevMakeCurrent( Context, Buffer, Buffer )) {
-      sprintf(exiterror, "Failure to Make Current\n");
-      exit(0);
-   }
-
-   InitializeMenus();
-
-   if(ReshapeFunc)
-      ReshapeFunc(VarInfo.xres, VarInfo.yres);
-   Redisplay = 1;
-}
-
 static void SignalWinch(int arg)
 {
    /* we can't change bitdepth without destroying the visual */
@@ -708,10 +742,7 @@ static void SignalWinch(int arg)
    VarInfo.blue = blue;
    VarInfo.transp = transp;
 
-   SetVideoMode();
-   CreateBuffer();
-
-   ResizeVisual();
+   Resized = 1;
 }
 
 int glutCreateWindow (const char *title)
@@ -786,6 +817,7 @@ void glutDestroyWindow(int win)
    glFBDevDestroyContext(Context);
    glFBDevDestroyBuffer(Buffer);
    glFBDevDestroyVisual(Visual);
+  
    Visual = NULL;
 }
 
@@ -803,12 +835,14 @@ void glutSwapBuffers(void)
 {
    glFlush();
 
+   if(!(DisplayMode & GLUT_DOUBLE))
+      return;
+
    if(ActiveMenu)
       DrawMenus();
-   if(MouseEnabled)
-      DrawCursor();
+   DrawCursor();
 
-   if(DisplayMode & GLUT_DOUBLE && Visible) {
+   if(Visible) {
       Swapping = 1;
       glFBDevSwapBuffers(Buffer);
       Swapping = 0;
@@ -837,10 +871,8 @@ void glutReshapeWindow(int width, int height)
    signal(SIGWINCH, SIG_IGN);
 
    SetVideoMode();
-   CreateBuffer();
-
-   ResizeVisual();
    signal(SIGWINCH, SignalWinch);
+   Resized = 1;
 }
 
 void glutFullScreen(void)