@@ -61,7 +61,6 @@ bt_context_t *jl_to_bt_context(void *sigctx)
6161#endif
6262}
6363
64-
6564static int thread0_exit_count = 0 ;
6665static void jl_exit_thread0 (int exitstate , jl_bt_element_t * bt_data , size_t bt_size );
6766
@@ -519,17 +518,22 @@ JL_DLLEXPORT int jl_profile_start_timer(void)
519518 sigprof .sigev_notify = SIGEV_SIGNAL ;
520519 sigprof .sigev_signo = SIGUSR1 ;
521520 sigprof .sigev_value .sival_ptr = & timerprof ;
522- if (timer_create (CLOCK_REALTIME , & sigprof , & timerprof ) == -1 )
521+ // Because SIGUSR1 is multipurpose, set `running` before so that we know that the first SIGUSR1 came from the timer
522+ running = 1 ;
523+ if (timer_create (CLOCK_REALTIME , & sigprof , & timerprof ) == -1 ) {
524+ running = 0 ;
523525 return -2 ;
526+ }
524527
525528 // Start the timer
526529 itsprof .it_interval .tv_sec = 0 ;
527530 itsprof .it_interval .tv_nsec = 0 ;
528531 itsprof .it_value .tv_sec = nsecprof / GIGA ;
529532 itsprof .it_value .tv_nsec = nsecprof % GIGA ;
530- if (timer_settime (timerprof , 0 , & itsprof , NULL ) == -1 )
533+ if (timer_settime (timerprof , 0 , & itsprof , NULL ) == -1 ) {
534+ running = 0 ;
531535 return -3 ;
532- running = 1 ;
536+ }
533537 return 0 ;
534538}
535539
@@ -648,6 +652,18 @@ static void kqueue_signal(int *sigqueue, struct kevent *ev, int sig)
648652}
649653#endif
650654
655+ void trigger_profile_peek (void )
656+ {
657+ jl_safe_printf ("\n======================================================================================\n" );
658+ jl_safe_printf ("Information request received. A stacktrace will print followed by a %.1f second profile\n" , profile_peek_duration );
659+ jl_safe_printf ("======================================================================================\n" );
660+ bt_size_cur = 0 ; // clear profile buffer
661+ if (jl_profile_start_timer () < 0 )
662+ jl_safe_printf ("ERROR: Could not start profile timer\n" );
663+ else
664+ profile_autostop_time = jl_hrtime () + (profile_peek_duration * 1e9 );
665+ }
666+
651667static void * signal_listener (void * arg )
652668{
653669 static jl_bt_element_t bt_data [JL_MAX_BT_SIZE + 1 ];
@@ -753,11 +769,17 @@ static void *signal_listener(void *arg)
753769
754770 int doexit = critical ;
755771#ifdef SIGINFO
756- if (sig == SIGINFO )
772+ if (sig == SIGINFO ) {
773+ if (running != 1 )
774+ trigger_profile_peek ();
757775 doexit = 0 ;
776+ }
758777#else
759- if (sig == SIGUSR1 )
778+ if (sig == SIGUSR1 ) {
779+ if (running != 1 )
780+ trigger_profile_peek ();
760781 doexit = 0 ;
782+ }
761783#endif
762784
763785 bt_size = 0 ;
@@ -835,6 +857,7 @@ static void *signal_listener(void *arg)
835857 }
836858#ifndef HAVE_MACH
837859 if (profile && running ) {
860+ jl_check_profile_autostop ();
838861#if defined(HAVE_TIMER )
839862 timer_settime (timerprof , 0 , & itsprof , NULL );
840863#elif defined(HAVE_ITIMER )
0 commit comments