[Gc] On cancellation, GC_thread_exit_proc is never called

NIIBE Yutaka gniibe at fsij.org
Mon Mar 29 20:48:08 PST 2010


Debugging Gauche (a Scheme interpreter) on *-linux-gnu host, I found
that pthread_support.c/GC_thread_exit_proc is never called when the
thread is cancelled.

I have investigated this problem.  Here is the case:

(0) The -fexceptions switch
(0-1) GC library is compiled with "-fexceptions" option of GCC.
(0-2) Gauche is compiled with no "-fexceptions" option.

(1) GC_thread_exit_proc should be registered by pthread_cleanup_push.
    In case of -fexceptions, __cleanup__ attribute is used and it is
    recorded in the .eh_frame section.
    Without option of -fexceptions, it is registered by

(2) The thread is cancelled by pthread_cancel.

(3) In the NPTL implementation of pthread library, the thread
    call __do_cancel, __pthread_unwind, and _Unwind_ForcedUnwind.

(4) Because Gauche is not compiled with "-fexceptions", we cannot
    find FDE for binary of Gauche, thus, unwinding can't call

If "-fexceptions" is not the requirement for gc users, I think that we
should use __pthread_register_cancel version of pthread_cleanup_push.
Here is a proposal patch.

I tried to undefine __EXCEPTIONS in pthread_support.h, but no success.

We needed to check GC_LINUX_THREADS, and undefine of __EXCEPTIONS should
be before the inclusion of <pthread.h>.

2010-03-30  NIIBE Yutaka  <gniibe at fsij.org>

	* include/gc_config_macros.h: Undefine __EXCEPTIONS when
          GC_LINUX_THREADS is defined.

Index: include/gc_config_macros.h
RCS file: /cvsroot/bdwgc/bdwgc/include/gc_config_macros.h,v
retrieving revision 1.22
diff -u -r1.22 gc_config_macros.h
--- include/gc_config_macros.h	20 Oct 2009 21:27:26 -0000	1.22
+++ include/gc_config_macros.h	30 Mar 2010 04:15:22 -0000
@@ -139,6 +139,20 @@
 # define _REENTRANT

+# if defined(GC_LINUX_THREADS)
+  /* We undefine __EXCEPTIONS to avoid using __cleanup__ attribute of GCC.   */
+  /*                                                                         */
+  /* NPTL implementation of pthread_cleanup_push uses __cleanup__ attribute  */
+  /* when __EXCEPTIONS is defined (-fexceptions).                            */
+  /* Stack unwinding and cleanup with __cleanup__ attributes works correctly */
+  /* when everything is compiled with -fexceptions, but it is not the        */
+  /* requirement for this library users to use -fexceptions everywhere.      */
+  /*                                                                         */
+  /* With __EXCEPTIONS undefined, cleanup routines are registered with       */
+  /* __pthread_register_cancel, which works any cases.                       */
+# undef __EXCEPTIONS
+# endif
 #define __GC
 #if !defined(_WIN32_WCE) || defined(__GNUC__)
 # include <stddef.h>

More information about the Gc mailing list