Skip to content

Commit 8d32959

Browse files
kevgssvoj
authored andcommitted
fix data races
srv_last_monitor_time: make all accesses relaxed atomical WARNING: ThreadSanitizer: data race (pid=12041) Write of size 8 at 0x000003949278 by thread T26 (mutexes: write M226445748578513120): #0 thd_destructor_proxy storage/innobase/handler/ha_innodb.cc:314:14 (mysqld+0x19b5505) Previous read of size 8 at 0x000003949278 by main thread: #0 innobase_init(void*) storage/innobase/handler/ha_innodb.cc:4180:11 (mysqld+0x1a03404) #1 ha_initialize_handlerton(st_plugin_int*) sql/handler.cc:522:31 (mysqld+0xc5ec73) #2 plugin_initialize(st_mem_root*, st_plugin_int*, int*, char**, bool) sql/sql_plugin.cc:1447:9 (mysqld+0x134908d) #3 plugin_init(int*, char**, int) sql/sql_plugin.cc:1729:15 (mysqld+0x13484f0) #4 init_server_components() sql/mysqld.cc:5345:7 (mysqld+0xbf720f) #5 mysqld_main(int, char**) sql/mysqld.cc:5940:7 (mysqld+0xbf107d) #6 main sql/main.cc:25:10 (mysqld+0xbe971b) Location is global 'srv_running' of size 8 at 0x000003949278 (mysqld+0x000003949278) WARNING: ThreadSanitizer: data race (pid=27869) Atomic write of size 4 at 0x7b4800000c00 by thread T8: #0 __tsan_atomic32_exchange llvm/projects/compiler-rt/lib/tsan/rtl/tsan_interface_atomic.cc:589 (mysqld+0xbd4eac) #1 TTASEventMutex<GenericPolicy>::exit() storage/innobase/include/ib0mutex.h:467:7 (mysqld+0x1a8d4cb) #2 PolicyMutex<TTASEventMutex<GenericPolicy> >::exit() storage/innobase/include/ib0mutex.h:609:10 (mysqld+0x1a7839e) #3 fil_validate() storage/innobase/fil/fil0fil.cc:5535:2 (mysqld+0x1abd913) #4 fil_validate_skip() storage/innobase/fil/fil0fil.cc:204:9 (mysqld+0x1aba601) #5 fil_aio_wait(unsigned long) storage/innobase/fil/fil0fil.cc:5296:2 (mysqld+0x1abbae6) #6 io_handler_thread storage/innobase/srv/srv0start.cc:340:3 (mysqld+0x21abe1e) Previous read of size 4 at 0x7b4800000c00 by main thread (mutexes: write M1273, write M1271): #0 TTASEventMutex<GenericPolicy>::state() const storage/innobase/include/ib0mutex.h:530:10 (mysqld+0x21c66e2) #1 sync_array_detect_deadlock(sync_array_t*, sync_cell_t*, sync_cell_t*, unsigned long) storage/innobase/sync/sync0arr.cc:746:14 (mysqld+0x21c1c7a) #2 sync_array_wait_event(sync_array_t*, sync_cell_t*&) storage/innobase/sync/sync0arr.cc:465:6 (mysqld+0x21c1708) #3 TTASEventMutex<GenericPolicy>::enter(unsigned int, unsigned int, char const*, unsigned int) storage/innobase/include/ib0mutex.h:516:6 (mysqld+0x1a8c206) #4 PolicyMutex<TTASEventMutex<GenericPolicy> >::enter(unsigned int, unsigned int, char const*, unsigned int) storage/innobase/include/ib0mutex.h:635:10 (mysqld+0x1a782c3) #5 fil_mutex_enter_and_prepare_for_io(unsigned long) storage/innobase/fil/fil0fil.cc:1131:3 (mysqld+0x1a9a92e) #6 fil_io(IORequest const&, bool, page_id_t const&, page_size_t const&, unsigned long, unsigned long, void*, void*, bool) storage/innobase/fil/fil0fil.cc:5082:2 (mysqld+0x1ab8de2) #7 buf_flush_write_block_low(buf_page_t*, buf_flush_t, bool) storage/innobase/buf/buf0flu.cc:1112:3 (mysqld+0x1cb970a) #8 buf_flush_page(buf_pool_t*, buf_page_t*, buf_flush_t, bool) storage/innobase/buf/buf0flu.cc:1270:3 (mysqld+0x1cb7d70) #9 buf_flush_try_neighbors(page_id_t const&, buf_flush_t, unsigned long, unsigned long) storage/innobase/buf/buf0flu.cc:1493:9 (mysqld+0x1cc9674) #10 buf_flush_page_and_try_neighbors(buf_page_t*, buf_flush_t, unsigned long, unsigned long*) storage/innobase/buf/buf0flu.cc:1565:13 (mysqld+0x1cbadf3) #11 buf_do_flush_list_batch(buf_pool_t*, unsigned long, unsigned long) storage/innobase/buf/buf0flu.cc:1825:3 (mysqld+0x1cbbcb8) #12 buf_flush_batch(buf_pool_t*, buf_flush_t, unsigned long, unsigned long, flush_counters_t*) storage/innobase/buf/buf0flu.cc:1895:16 (mysqld+0x1cbb459) #13 buf_flush_do_batch(buf_pool_t*, buf_flush_t, unsigned long, unsigned long, flush_counters_t*) storage/innobase/buf/buf0flu.cc:2065:2 (mysqld+0x1cbcfe1) #14 buf_flush_lists(unsigned long, unsigned long, unsigned long*) storage/innobase/buf/buf0flu.cc:2167:8 (mysqld+0x1cbd5a3) #15 log_preflush_pool_modified_pages(unsigned long) storage/innobase/log/log0log.cc:1400:13 (mysqld+0x1eefc3b) #16 log_make_checkpoint_at(unsigned long, bool) storage/innobase/log/log0log.cc:1751:10 (mysqld+0x1eefb16) #17 buf_dblwr_create() storage/innobase/buf/buf0dblwr.cc:335:2 (mysqld+0x1cd2141) #18 innobase_start_or_create_for_mysql() storage/innobase/srv/srv0start.cc:2539:10 (mysqld+0x21b4d8e) #19 innobase_init(void*) storage/innobase/handler/ha_innodb.cc:4193:8 (mysqld+0x1a5e3d7) #20 ha_initialize_handlerton(st_plugin_int*) sql/handler.cc:522:31 (mysqld+0xc74d33) #21 plugin_initialize(st_mem_root*, st_plugin_int*, int*, char**, bool) sql/sql_plugin.cc:1447:9 (mysqld+0x1376d5d) #22 plugin_init(int*, char**, int) sql/sql_plugin.cc:1729:15 (mysqld+0x13761c0) #23 init_server_components() sql/mysqld.cc:5348:7 (mysqld+0xc0d0ff) #24 mysqld_main(int, char**) sql/mysqld.cc:5943:7 (mysqld+0xc06f9d) #25 main sql/main.cc:25:10 (mysqld+0xbff71b) WARNING: ThreadSanitizer: data race (pid=29031) Write of size 8 at 0x0000039e48e0 by thread T15: #0 srv_monitor_thread storage/innobase/srv/srv0srv.cc:1699:24 (mysqld+0x21a254e) Previous write of size 8 at 0x0000039e48e0 by thread T14: #0 srv_refresh_innodb_monitor_stats() storage/innobase/srv/srv0srv.cc:1165:24 (mysqld+0x21a3124) #1 srv_error_monitor_thread storage/innobase/srv/srv0srv.cc:1836:3 (mysqld+0x21a2d40) Location is global 'srv_last_monitor_time' of size 8 at 0x0000039e48e0 (mysqld+0x0000039e48e0)
1 parent 03a80e2 commit 8d32959

File tree

5 files changed

+34
-20
lines changed

5 files changed

+34
-20
lines changed

storage/innobase/handler/ha_innodb.cc

Lines changed: 15 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -305,7 +305,7 @@ is_partition(
305305

306306
/** Signal to shut down InnoDB (NULL if shutdown was signaled, or if
307307
running in innodb_read_only mode, srv_read_only_mode) */
308-
volatile st_my_thread_var *srv_running;
308+
st_my_thread_var *srv_running;
309309
/** Service thread that waits for the server shutdown and stops purge threads.
310310
Purge workers have THDs that are needed to calculate virtual columns.
311311
This THDs must be destroyed rather early in the server shutdown sequence.
@@ -332,12 +332,14 @@ thd_destructor_proxy(void *)
332332
myvar->current_cond = &thd_destructor_cond;
333333

334334
mysql_mutex_lock(&thd_destructor_mutex);
335-
srv_running = myvar;
335+
my_atomic_storeptr_explicit(&srv_running, myvar,
336+
MY_MEMORY_ORDER_RELAXED);
336337
/* wait until the server wakes the THD to abort and die */
337338
while (!srv_running->abort)
338339
mysql_cond_wait(&thd_destructor_cond, &thd_destructor_mutex);
339340
mysql_mutex_unlock(&thd_destructor_mutex);
340-
srv_running = NULL;
341+
my_atomic_storeptr_explicit(&srv_running, NULL,
342+
MY_MEMORY_ORDER_RELAXED);
341343

342344
while (srv_fast_shutdown == 0 &&
343345
(trx_sys_any_active_transactions() ||
@@ -4333,7 +4335,8 @@ innobase_init(
43334335
mysql_thread_create(thd_destructor_thread_key,
43344336
&thd_destructor_thread,
43354337
NULL, thd_destructor_proxy, NULL);
4336-
while (!srv_running)
4338+
while (!my_atomic_loadptr_explicit(&srv_running,
4339+
MY_MEMORY_ORDER_RELAXED))
43374340
os_thread_sleep(20);
43384341
}
43394342

@@ -4427,10 +4430,12 @@ innobase_end(handlerton*, ha_panic_function)
44274430
hash_table_free(innobase_open_tables);
44284431
innobase_open_tables = NULL;
44294432

4430-
if (!abort_loop && srv_running) {
4433+
st_my_thread_var* running = my_atomic_loadptr_explicit(
4434+
&srv_running, MY_MEMORY_ORDER_RELAXED);
4435+
if (!abort_loop && running) {
44314436
// may be UNINSTALL PLUGIN statement
4432-
srv_running->abort = 1;
4433-
mysql_cond_broadcast(srv_running->current_cond);
4437+
running->abort = 1;
4438+
mysql_cond_broadcast(running->current_cond);
44344439
}
44354440

44364441
if (!srv_read_only_mode) {
@@ -17764,7 +17769,9 @@ fast_shutdown_validate(
1776417769

1776517770
uint new_val = *reinterpret_cast<uint*>(save);
1776617771

17767-
if (srv_fast_shutdown && !new_val && !srv_running) {
17772+
if (srv_fast_shutdown && !new_val
17773+
&& !my_atomic_loadptr_explicit(&srv_running,
17774+
MY_MEMORY_ORDER_RELAXED)) {
1776817775
return(1);
1776917776
}
1777017777

storage/innobase/include/ib0mutex.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -527,7 +527,8 @@ struct TTASEventMutex {
527527
int32 state() const
528528
UNIV_NOTHROW
529529
{
530-
return(m_lock_word);
530+
return(my_atomic_load32_explicit(&m_lock_word,
531+
MY_MEMORY_ORDER_RELAXED));
531532
}
532533

533534
/** The event that the mutex will wait in sync0arr.cc

storage/innobase/include/srv0srv.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -476,7 +476,7 @@ extern uint srv_fast_shutdown; /*!< If this is 1, do not do a
476476

477477
/** Signal to shut down InnoDB (NULL if shutdown was signaled, or if
478478
running in innodb_read_only mode, srv_read_only_mode) */
479-
extern volatile st_my_thread_var *srv_running;
479+
extern st_my_thread_var *srv_running;
480480

481481
extern ibool srv_innodb_status;
482482

storage/innobase/srv/srv0srv.cc

Lines changed: 14 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1170,7 +1170,16 @@ srv_refresh_innodb_monitor_stats(void)
11701170
{
11711171
mutex_enter(&srv_innodb_monitor_mutex);
11721172

1173-
srv_last_monitor_time = time(NULL);
1173+
time_t current_time = time(NULL);
1174+
1175+
if (difftime(current_time, srv_last_monitor_time) <= 60) {
1176+
/* We referesh InnoDB Monitor values so that averages are
1177+
printed from at most 60 last seconds */
1178+
mutex_exit(&srv_innodb_monitor_mutex);
1179+
return;
1180+
}
1181+
1182+
srv_last_monitor_time = current_time;
11741183

11751184
os_aio_refresh_stats();
11761185

@@ -1792,6 +1801,8 @@ DECLARE_THREAD(srv_monitor_thread)(void*)
17921801
}
17931802
}
17941803

1804+
srv_refresh_innodb_monitor_stats();
1805+
17951806
if (srv_shutdown_state != SRV_SHUTDOWN_NONE) {
17961807
goto exit_func;
17971808
}
@@ -1863,13 +1874,6 @@ DECLARE_THREAD(srv_error_monitor_thread)(void*)
18631874
old_lsn = new_lsn;
18641875
}
18651876

1866-
if (difftime(time(NULL), srv_last_monitor_time) > 60) {
1867-
/* We referesh InnoDB Monitor values so that averages are
1868-
printed from at most 60 last seconds */
1869-
1870-
srv_refresh_innodb_monitor_stats();
1871-
}
1872-
18731877
/* Update the statistics collected for deciding LRU
18741878
eviction policy. */
18751879
buf_LRU_stat_update();
@@ -2938,7 +2942,8 @@ srv_purge_wakeup()
29382942

29392943
srv_release_threads(SRV_WORKER, n_workers);
29402944
}
2941-
} while (!srv_running
2945+
} while (!my_atomic_loadptr_explicit(&srv_running,
2946+
MY_MEMORY_ORDER_RELAXED)
29422947
&& (srv_sys.n_threads_active[SRV_WORKER]
29432948
|| srv_sys.n_threads_active[SRV_PURGE]));
29442949
}

storage/innobase/srv/srv0start.cc

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2840,7 +2840,8 @@ srv_shutdown_bg_undo_sources()
28402840
void
28412841
innodb_shutdown()
28422842
{
2843-
ut_ad(!srv_running);
2843+
ut_ad(!my_atomic_loadptr_explicit(&srv_running,
2844+
MY_MEMORY_ORDER_RELAXED));
28442845
ut_ad(!srv_undo_sources);
28452846

28462847
switch (srv_operation) {

0 commit comments

Comments
 (0)