예제 #1
0
파일: threads.c 프로젝트: liballeg/allegro5
/* Function: al_join_thread
 */
void al_join_thread(ALLEGRO_THREAD *thread, void **ret_value)
{
   ASSERT(thread);

   /* If al_join_thread() is called soon after al_start_thread(), the thread
    * function may not yet have noticed the STARTING state and executed the
    * user's thread function.  Hence we must wait until the thread enters the
    * STARTED state.
    */
   while (thread->thread_state == THREAD_STATE_STARTING) {
      al_rest(0.001);
   }

   switch (thread->thread_state) {
      case THREAD_STATE_CREATED: /* fall through */
      case THREAD_STATE_STARTED:
         _al_mutex_lock(&thread->mutex);
         thread->thread_state = THREAD_STATE_JOINING;
         _al_cond_broadcast(&thread->cond);
         _al_mutex_unlock(&thread->mutex);
         _al_cond_destroy(&thread->cond);
         _al_mutex_destroy(&thread->mutex);
         _al_thread_join(&thread->thread);
         thread->thread_state = THREAD_STATE_JOINED;
         break;
      case THREAD_STATE_STARTING:
         ASSERT(thread->thread_state != THREAD_STATE_STARTING);
         break;
      case THREAD_STATE_JOINING:
         ASSERT(thread->thread_state != THREAD_STATE_JOINING);
         break;
      case THREAD_STATE_JOINED:
         ASSERT(thread->thread_state != THREAD_STATE_JOINED);
         break;
      case THREAD_STATE_DESTROYED:
         ASSERT(thread->thread_state != THREAD_STATE_DESTROYED);
         break;
      case THREAD_STATE_DETACHED:
         ASSERT(thread->thread_state != THREAD_STATE_DETACHED);
         break;
   }

   if (ret_value) {
      *ret_value = thread->retval;
   }
}
static void xglx_shutdown_system(void)
{
   ALLEGRO_SYSTEM *s = al_get_system_driver();
   ALLEGRO_SYSTEM_XGLX *sx = (void *)s;

   ALLEGRO_INFO("shutting down.\n");

   if (sx->x11display) {
      /* Events thread only runs if we are connected to an X server. */
      _al_thread_join(&sx->thread);
   }

   /* Close all open displays. */
   while (_al_vector_size(&s->displays) > 0) {
      ALLEGRO_DISPLAY **dptr = _al_vector_ref(&s->displays, 0);
      ALLEGRO_DISPLAY *d = *dptr;
      _al_destroy_display_bitmaps(d);
      al_destroy_display(d);
   }
   _al_vector_free(&s->displays);

   // Makes sure we wait for any commands sent to the X server when destroying the displays.
   // Should make sure we don't shutdown before modes are restored.
   if (sx->x11display) {
      XSync(sx->x11display, False);
   }
   
   _al_xsys_mmon_exit(sx);

   if (sx->x11display) {
      XCloseDisplay(sx->x11display);
      sx->x11display = None;
      ALLEGRO_DEBUG("xsys: close x11display.\n");
   }

   if (sx->gfxdisplay) {
      /* XXX for some reason, crashes if both XCloseDisplay calls are made */
      /* XCloseDisplay(sx->gfxdisplay); */
      sx->gfxdisplay = None;
   }

   al_free(sx);
}
예제 #3
0
static void xglx_shutdown_system(void)
{
   ALLEGRO_SYSTEM *s = al_get_system_driver();
   ALLEGRO_SYSTEM_XGLX *sx = (void *)s;

   ALLEGRO_INFO("shutting down.\n");

   if (sx->have_xevents_thread) {
      _al_thread_join(&sx->xevents_thread);
      sx->have_xevents_thread = false;
   }

   /* Close all open displays. */
   while (_al_vector_size(&s->displays) > 0) {
      ALLEGRO_DISPLAY **dptr = _al_vector_ref(&s->displays, 0);
      ALLEGRO_DISPLAY *d = *dptr;
      al_destroy_display(d);
   }
   _al_vector_free(&s->displays);

   // Makes sure we wait for any commands sent to the X server when destroying the displays.
   // Should make sure we don't shutdown before modes are restored.
   if (sx->x11display) {
      XSync(sx->x11display, False);
   }

   _al_xsys_mmon_exit(sx);

   if (sx->x11display) {
      XCloseDisplay(sx->x11display);
      sx->x11display = None;
      ALLEGRO_DEBUG("xsys: close x11display.\n");
   }

   if (sx->gfxdisplay) {
      XCloseDisplay(sx->gfxdisplay);
      sx->gfxdisplay = None;
   }

   al_free(sx);
}
예제 #4
0
static void xglx_shutdown_system(void)
{
   /* Close all open displays. */
   ALLEGRO_SYSTEM *s = al_get_system_driver();
   ALLEGRO_SYSTEM_XGLX *sx = (void *)s;

   ALLEGRO_INFO("shutting down.\n");

   _al_thread_join(&sx->thread);

   while (_al_vector_size(&s->displays) > 0) {
      ALLEGRO_DISPLAY **dptr = _al_vector_ref(&s->displays, 0);
      ALLEGRO_DISPLAY *d = *dptr;
      _al_destroy_display_bitmaps(d);
      al_destroy_display(d);
   }
   _al_vector_free(&s->displays);

   _al_xglx_free_mode_infos(sx);

#ifdef ALLEGRO_XWINDOWS_WITH_XINERAMA
   _al_xsys_xinerama_exit(sx);
#endif

   if (sx->x11display) {
      XCloseDisplay(sx->x11display);
      sx->x11display = None;
   }

   if (sx->gfxdisplay) {
      /* XXX for some reason, crashes if both XCloseDisplay calls are made */
      /* XCloseDisplay(sx->gfxdisplay); */
      sx->gfxdisplay = None;
   }

   _AL_FREE(sx);
}