@@ -722,7 +722,7 @@ static void JuliaInitializeLongjmpXorKey(void)
722
722
}
723
723
#endif
724
724
725
- JL_UNUSED static uintptr_t ptr_demangle (uintptr_t p )
725
+ JL_UNUSED static uintptr_t ptr_demangle (uintptr_t p ) JL_NOTSAFEPOINT
726
726
{
727
727
#if defined(__GLIBC__ )
728
728
#if defined(_CPU_X86_ )
@@ -854,7 +854,7 @@ _os_ptr_munge(uintptr_t ptr)
854
854
855
855
extern bt_context_t * jl_to_bt_context (void * sigctx );
856
856
857
- void jl_rec_backtrace (jl_task_t * t )
857
+ void jl_rec_backtrace (jl_task_t * t ) JL_NOTSAFEPOINT
858
858
{
859
859
jl_task_t * ct = jl_current_task ;
860
860
jl_ptls_t ptls = ct -> ptls ;
@@ -1104,7 +1104,9 @@ JL_DLLEXPORT void jlbacktrace(void) JL_NOTSAFEPOINT
1104
1104
jl_print_bt_entry_codeloc (bt_data + i );
1105
1105
}
1106
1106
}
1107
- JL_DLLEXPORT void jlbacktracet (jl_task_t * t )
1107
+
1108
+ // Print backtrace for specified task
1109
+ JL_DLLEXPORT void jlbacktracet (jl_task_t * t ) JL_NOTSAFEPOINT
1108
1110
{
1109
1111
jl_task_t * ct = jl_current_task ;
1110
1112
jl_ptls_t ptls = ct -> ptls ;
@@ -1121,6 +1123,42 @@ JL_DLLEXPORT void jl_print_backtrace(void) JL_NOTSAFEPOINT
1121
1123
jlbacktrace ();
1122
1124
}
1123
1125
1126
+ // Print backtraces for all live tasks, for all threads.
1127
+ // WARNING: this is dangerous and can crash if used outside of gdb, if
1128
+ // all of Julia's threads are not stopped!
1129
+ JL_DLLEXPORT void jl_print_task_backtraces (void ) JL_NOTSAFEPOINT
1130
+ {
1131
+ for (size_t i = 0 ; i < jl_n_threads ; i ++ ) {
1132
+ jl_ptls_t ptls2 = jl_all_tls_states [i ];
1133
+ arraylist_t * live_tasks = & ptls2 -> heap .live_tasks ;
1134
+ size_t n = live_tasks -> len ;
1135
+ jl_safe_printf ("==== Thread %d created %zu live tasks\n" ,
1136
+ ptls2 -> tid + 1 , n + 1 );
1137
+ jl_safe_printf (" ---- Root task (%p)\n" , ptls2 -> root_task );
1138
+ jl_safe_printf (" (sticky: %d, started: %d, state: %d, tid: %d)\n" ,
1139
+ ptls2 -> root_task -> sticky , ptls2 -> root_task -> started ,
1140
+ jl_atomic_load_relaxed (& ptls2 -> root_task -> _state ),
1141
+ jl_atomic_load_relaxed (& ptls2 -> root_task -> tid ) + 1 );
1142
+ jlbacktracet (ptls2 -> root_task );
1143
+
1144
+ void * * lst = live_tasks -> items ;
1145
+ for (size_t j = 0 ; j < live_tasks -> len ; j ++ ) {
1146
+ jl_task_t * t = (jl_task_t * )lst [j ];
1147
+ jl_safe_printf (" ---- Task %zu (%p)\n" , j + 1 , t );
1148
+ jl_safe_printf (" (sticky: %d, started: %d, state: %d, tid: %d)\n" ,
1149
+ t -> sticky , t -> started , jl_atomic_load_relaxed (& t -> _state ),
1150
+ jl_atomic_load_relaxed (& t -> tid ) + 1 );
1151
+ if (t -> stkbuf != NULL )
1152
+ jlbacktracet (t );
1153
+ else
1154
+ jl_safe_printf (" no stack\n" );
1155
+ jl_safe_printf (" ---- End task %zu\n" , j + 1 );
1156
+ }
1157
+ jl_safe_printf ("==== End thread %d\n" , ptls2 -> tid + 1 );
1158
+ }
1159
+ jl_safe_printf ("==== Done\n" );
1160
+ }
1161
+
1124
1162
#ifdef __cplusplus
1125
1163
}
1126
1164
#endif
0 commit comments