diff --git a/storage/innobase/include/os0thread.h b/storage/innobase/include/os0thread.h index 07f9e14..eab0f67 100644 --- a/storage/innobase/include/os0thread.h +++ b/storage/innobase/include/os0thread.h @@ -115,9 +115,23 @@ os_thread_create_func( os_thread_id_t* thread_id); /*!< out: id of the created thread, or NULL */ -/** Exits the current thread. */ +/** +Waits until the specified thread completes and joins it. Its return value is +ignored. + +@param thread thread to join */ +void +os_thread_join( + os_thread_id_t thread); + +/** +Exits the current thread. + +@param detach if true, the thread will be detached right before exiting. If +false, another thread is responsible for joining this thread */ void -os_thread_exit() +os_thread_exit( + bool detach = true) UNIV_COLD MY_ATTRIBUTE((noreturn)); /*****************************************************************//** diff --git a/storage/innobase/include/row0ftsort.h b/storage/innobase/include/row0ftsort.h index 50d80f5..5713822 100644 --- a/storage/innobase/include/row0ftsort.h +++ b/storage/innobase/include/row0ftsort.h @@ -87,6 +87,7 @@ struct fts_psort_t { ulint state; /*!< parent thread state */ fts_doc_list_t fts_doc_list; /*!< doc list to process */ fts_psort_common_t* psort_common; /*!< ptr to all psort info */ + os_thread_id_t thread_hdl; /*!< thread handle */ dberr_t error; /*!< db error during psort */ ulint memory_used; /*!< memory used by fts_doc_list */ ib_mutex_t mutex; /*!< mutex for fts_doc_list */ diff --git a/storage/innobase/os/os0thread.cc b/storage/innobase/os/os0thread.cc index d8691b1..9b7f5ea 100644 --- a/storage/innobase/os/os0thread.cc +++ b/storage/innobase/os/os0thread.cc @@ -188,9 +188,30 @@ os_thread_create_func( } } -/** Exits the current thread. */ +/** +Waits until the specified thread completes and joins it. Its return value is +ignored. + +@param thread thread to join */ +void +os_thread_join( + os_thread_id_t thread) +{ + int ret MY_ATTRIBUTE((unused)) = pthread_join(thread, NULL); + + /* Waiting on already-quit threads is allowed */ + ut_ad(ret == 0 || ret == ESRCH); +} + + +/** +Exits the current thread. + +@param detach if true, the thread will be detached right before exiting. If +false, another thread is responsible for joining this thread */ void -os_thread_exit() +os_thread_exit( + bool detach) { #ifdef UNIV_DEBUG_THREAD_CREATION ib::info() << "Thread exits, id " @@ -217,7 +238,8 @@ os_thread_exit() ExitThread(0); #else mutex_exit(&thread_mutex); - pthread_detach(pthread_self()); + if (detach) + pthread_detach(pthread_self()); pthread_exit(NULL); #endif } diff --git a/storage/innobase/row/row0ftsort.cc b/storage/innobase/row/row0ftsort.cc index 7d78f68..cea6a30 100644 --- a/storage/innobase/row/row0ftsort.cc +++ b/storage/innobase/row/row0ftsort.cc @@ -1069,7 +1069,7 @@ fts_parallel_merge( os_event_set(psort_info->psort_common->merge_event); psort_info->child_status = FTS_CHILD_EXITING; - os_thread_exit(); + os_thread_exit(false); OS_THREAD_DUMMY_RETURN; } @@ -1082,7 +1082,6 @@ row_fts_start_parallel_merge( fts_psort_t* merge_info) /*!< in: parallel sort info */ { int i = 0; - os_thread_id_t thd_id; /* Kick off merge/insert threads */ for (i = 0; i < FTS_NUM_AUX_INDEX; i++) { @@ -1091,7 +1090,7 @@ row_fts_start_parallel_merge( os_thread_create(fts_parallel_merge, (void*) &merge_info[i], - &thd_id); + &merge_info[i].thread_hdl); } } diff --git a/storage/innobase/row/row0merge.cc b/storage/innobase/row/row0merge.cc index 22ab3ea..71b3fd4 100644 --- a/storage/innobase/row/row0merge.cc +++ b/storage/innobase/row/row0merge.cc @@ -4486,6 +4486,13 @@ wait_again: " threads exited when creating" " FTS index '" << indexes[i]->name << "'"; + } else { + for (j = 0; j < FTS_NUM_AUX_INDEX; + j++) { + + os_thread_join(merge_info[j] + .thread_hdl); + } } } else { /* This cannot report duplicates; an