diff --git a/common.cpp b/common.cpp index f338b9019..20840c4ad 100644 --- a/common.cpp +++ b/common.cpp @@ -1952,6 +1952,7 @@ void set_main_thread() { /* Notice when we've forked */ static pid_t initial_pid; + bool is_forked_child(void) { bool is_child_of_fork = (getpid() != initial_pid); if (is_child_of_fork) { diff --git a/exec.cpp b/exec.cpp index 6f3ae5498..f96fcf3f1 100644 --- a/exec.cpp +++ b/exec.cpp @@ -1237,6 +1237,8 @@ void exec( parser_t &parser, job_t *j ) std::string actual_cmd_str = wcs2string(p->actual_cmd); const char *actual_cmd = actual_cmd_str.c_str(); + const wchar_t *reader_current_filename(); + printf("forking for '%s' in '%ls'\n", actual_cmd, reader_current_filename()); pid = execute_fork(true /* must drain threads */); if( pid == 0 ) { diff --git a/fish.cpp b/fish.cpp index 6bfd37ca0..bf2784239 100644 --- a/fish.cpp +++ b/fish.cpp @@ -89,7 +89,7 @@ static int read_init() { wcstring config_dir_escaped = escape_string( config_dir, 1 ); wcstring eval_buff = format_string(L"builtin . %ls/config.fish 2>/dev/null", config_dir_escaped.c_str()); - parser.eval( eval_buff.c_str(), 0, TOP ); + parser.eval( eval_buff, 0, TOP ); } return 1; @@ -265,8 +265,9 @@ static int fish_parse_opt( int argc, char **argv, const char **cmd_ptr ) parses commands from stdin or files, depending on arguments */ +extern int g_fork_count; int main( int argc, char **argv ) -{ +{ struct stat tmp; int res=1; const char *cmd=0; @@ -304,6 +305,8 @@ int main( int argc, char **argv ) parser_t &parser = parser_t::principal_parser(); + printf("%d: g_fork_count: %d\n", __LINE__, g_fork_count); + if( read_init() ) { if( cmd != 0 ) @@ -387,5 +390,7 @@ int main( int argc, char **argv ) env_destroy(); + printf("%d: g_fork_count: %d\n", __LINE__, g_fork_count); + return res?STATUS_UNKNOWN_COMMAND:proc_get_last_status(); } diff --git a/iothread.cpp b/iothread.cpp index dcb79fe13..bcfe49438 100644 --- a/iothread.cpp +++ b/iothread.cpp @@ -199,8 +199,14 @@ void iothread_service_completion(void) { void iothread_drain_all(void) { ASSERT_IS_MAIN_THREAD(); - ASSERT_IS_NOT_FORKED_CHILD(); + ASSERT_IS_NOT_FORKED_CHILD(); + if (s_active_thread_count == 0) + return; + int thread_count = s_active_thread_count; + double now = timef(); while (s_active_thread_count > 0) { iothread_service_completion(); } + double after = timef(); + printf("(Waited %.02f msec for %d thread(s) to drain)\n", 1000 * (after - now), thread_count); } diff --git a/postfork.cpp b/postfork.cpp index 1bb796280..523a78164 100644 --- a/postfork.cpp +++ b/postfork.cpp @@ -304,6 +304,8 @@ int setup_child_process( job_t *j, process_t *p ) } +int g_fork_count = 0; + /** This function is a wrapper around fork. If the fork calls fails with EAGAIN, it is retried FORK_LAPS times, with a very slight @@ -323,6 +325,8 @@ pid_t execute_fork(bool wait_for_threads_to_die) struct timespec pollint; int i; + g_fork_count++; + for( i=0; i