diff options
author | A. Unique TensorFlower <gardener@tensorflow.org> | 2017-11-21 23:05:17 -0800 |
---|---|---|
committer | TensorFlower Gardener <gardener@tensorflow.org> | 2017-11-21 23:08:52 -0800 |
commit | f93c48dc061d23495a4425fcad17d55159cb02b1 (patch) | |
tree | ee1210f8810e0b0fec9346f762e854b371899919 | |
parent | ef3ee202659a2a49afcd9898451bf9b1256a2757 (diff) |
Use LINKER_INITIALIZED for mutexes with static storage class.
This was causing exit-time races as some threads were accessing the
mutex as it was being destructed.
---------------
It is illegal to use any static type with a constructor/destructor with static
storage class in a multithreaded C++ programme that can exit(), even if the
constructor is protected by C++11's function-scope static initialization rules,
because exit-time destruction is unsafe in the presence of multiple threads.
For things that are not function-scope, the construction is also unsafe,
because global contruction ordering is undefined in general.
The LINKER_INITIALIZED variant constructor for TensorFlow's mutex avoids these
problems, at the cost of relying on the linker to zero-initialize the BSS
region.
PiperOrigin-RevId: 176612772
-rw-r--r-- | tensorflow/contrib/ffmpeg/default/ffmpeg_lib_test.cc | 2 | ||||
-rw-r--r-- | tensorflow/contrib/nccl/kernels/nccl_manager.cc | 2 | ||||
-rw-r--r-- | tensorflow/core/common_runtime/device_factory.cc | 2 | ||||
-rw-r--r-- | tensorflow/core/common_runtime/session_factory.cc | 2 | ||||
-rw-r--r-- | tensorflow/core/debug/debug_io_utils.cc | 2 | ||||
-rw-r--r-- | tensorflow/core/distributed_runtime/local_master.cc | 2 | ||||
-rw-r--r-- | tensorflow/core/distributed_runtime/server_lib.cc | 2 | ||||
-rw-r--r-- | tensorflow/core/framework/load_library.cc | 2 | ||||
-rw-r--r-- | tensorflow/core/framework/op_def_util.cc | 2 | ||||
-rw-r--r-- | tensorflow/core/kernels/meta_support.cc | 2 | ||||
-rw-r--r-- | tensorflow/core/lib/random/random.cc | 4 | ||||
-rw-r--r-- | tensorflow/core/platform/s3/s3_file_system.cc | 2 | ||||
-rw-r--r-- | tensorflow/python/lib/core/py_func.cc | 2 |
13 files changed, 14 insertions, 14 deletions
diff --git a/tensorflow/contrib/ffmpeg/default/ffmpeg_lib_test.cc b/tensorflow/contrib/ffmpeg/default/ffmpeg_lib_test.cc index 2871c14628..85b61b2616 100644 --- a/tensorflow/contrib/ffmpeg/default/ffmpeg_lib_test.cc +++ b/tensorflow/contrib/ffmpeg/default/ffmpeg_lib_test.cc @@ -39,7 +39,7 @@ const char kTestMp3Filename[] = // Set to true via a command line flag iff the test is expected to have FFmpeg // installed. -mutex mu; +mutex mu(LINKER_INITIALIZED); bool should_ffmpeg_be_installed GUARDED_BY(mu) = false; string ParseTestFlags(int* argc, char** argv) { diff --git a/tensorflow/contrib/nccl/kernels/nccl_manager.cc b/tensorflow/contrib/nccl/kernels/nccl_manager.cc index 1eb1481675..31a35b0d53 100644 --- a/tensorflow/contrib/nccl/kernels/nccl_manager.cc +++ b/tensorflow/contrib/nccl/kernels/nccl_manager.cc @@ -370,7 +370,7 @@ void NcclManager::AddParticipant(int num_devices, const string& key, } void NcclManager::RunCollective(const string& key, Collective* collective) { - static mutex collective_mu; + static mutex collective_mu(LINKER_INITIALIZED); auto* communicator = GetCommunicator(collective); collective->communicator = communicator; diff --git a/tensorflow/core/common_runtime/device_factory.cc b/tensorflow/core/common_runtime/device_factory.cc index fa12c48fb9..b43c718817 100644 --- a/tensorflow/core/common_runtime/device_factory.cc +++ b/tensorflow/core/common_runtime/device_factory.cc @@ -32,7 +32,7 @@ namespace tensorflow { namespace { static mutex* get_device_factory_lock() { - static mutex device_factory_lock; + static mutex device_factory_lock(LINKER_INITIALIZED); return &device_factory_lock; } diff --git a/tensorflow/core/common_runtime/session_factory.cc b/tensorflow/core/common_runtime/session_factory.cc index dba7a9253e..0234d4c372 100644 --- a/tensorflow/core/common_runtime/session_factory.cc +++ b/tensorflow/core/common_runtime/session_factory.cc @@ -29,7 +29,7 @@ namespace tensorflow { namespace { static mutex* get_session_factory_lock() { - static mutex session_factory_lock; + static mutex session_factory_lock(LINKER_INITIALIZED); return &session_factory_lock; } diff --git a/tensorflow/core/debug/debug_io_utils.cc b/tensorflow/core/debug/debug_io_utils.cc index 85d04daa65..f81445c20b 100644 --- a/tensorflow/core/debug/debug_io_utils.cc +++ b/tensorflow/core/debug/debug_io_utils.cc @@ -736,7 +736,7 @@ Status DebugGrpcChannel::ReceiveServerRepliesAndClose() { } } -mutex DebugGrpcIO::streams_mu; +mutex DebugGrpcIO::streams_mu(LINKER_INITIALIZED); int64 DebugGrpcIO::channel_connection_timeout_micros = 900 * 1000 * 1000; // TODO(cais): Make this configurable? diff --git a/tensorflow/core/distributed_runtime/local_master.cc b/tensorflow/core/distributed_runtime/local_master.cc index c7ba7abeaf..aaa4cfa734 100644 --- a/tensorflow/core/distributed_runtime/local_master.cc +++ b/tensorflow/core/distributed_runtime/local_master.cc @@ -159,7 +159,7 @@ Status LocalMaster::Reset(CallOptions* call_options, namespace { mutex* get_local_master_registry_lock() { - static mutex local_master_registry_lock; + static mutex local_master_registry_lock(LINKER_INITIALIZED); return &local_master_registry_lock; } diff --git a/tensorflow/core/distributed_runtime/server_lib.cc b/tensorflow/core/distributed_runtime/server_lib.cc index 0b7fed79cd..7d308bb723 100644 --- a/tensorflow/core/distributed_runtime/server_lib.cc +++ b/tensorflow/core/distributed_runtime/server_lib.cc @@ -24,7 +24,7 @@ namespace tensorflow { namespace { mutex* get_server_factory_lock() { - static mutex server_factory_lock; + static mutex server_factory_lock(LINKER_INITIALIZED); return &server_factory_lock; } diff --git a/tensorflow/core/framework/load_library.cc b/tensorflow/core/framework/load_library.cc index f825335300..b9e33b148f 100644 --- a/tensorflow/core/framework/load_library.cc +++ b/tensorflow/core/framework/load_library.cc @@ -45,7 +45,7 @@ struct Library { // perform initialization again, so the OpList would be empty. Status LoadLibrary(const char* library_filename, void** result, const void** buf, size_t* len) { - static mutex mu; + static mutex mu(LINKER_INITIALIZED); static std::unordered_map<string, Library> loaded_libs; Env* env = Env::Default(); Library library; diff --git a/tensorflow/core/framework/op_def_util.cc b/tensorflow/core/framework/op_def_util.cc index f7d4166f97..29feda499f 100644 --- a/tensorflow/core/framework/op_def_util.cc +++ b/tensorflow/core/framework/op_def_util.cc @@ -332,7 +332,7 @@ Status CheckOpDeprecation(const OpDef& op_def, int graph_def_version) { ". ", dep.explanation(), "."); } else { // Warn only once for each op name, and do it in a threadsafe manner. - static mutex mu; + static mutex mu(LINKER_INITIALIZED); static std::unordered_set<string> warned; bool warn; { diff --git a/tensorflow/core/kernels/meta_support.cc b/tensorflow/core/kernels/meta_support.cc index b29feb0032..9fed01189f 100644 --- a/tensorflow/core/kernels/meta_support.cc +++ b/tensorflow/core/kernels/meta_support.cc @@ -82,7 +82,7 @@ gemmlowp::WorkersPool* GetWorkersPool() { } mutex& GetMutex() { - static mutex mu; + static mutex mu(LINKER_INITIALIZED); return mu; } diff --git a/tensorflow/core/lib/random/random.cc b/tensorflow/core/lib/random/random.cc index 723c1100f8..82dc829507 100644 --- a/tensorflow/core/lib/random/random.cc +++ b/tensorflow/core/lib/random/random.cc @@ -33,14 +33,14 @@ std::mt19937_64 InitRngWithDefaultSeed() { return std::mt19937_64(); } uint64 New64() { static std::mt19937_64* rng = InitRngWithRandomSeed(); - static mutex mu; + static mutex mu(LINKER_INITIALIZED); mutex_lock l(mu); return (*rng)(); } uint64 New64DefaultSeed() { static std::mt19937_64 rng = InitRngWithDefaultSeed(); - static mutex mu; + static mutex mu(LINKER_INITIALIZED); mutex_lock l(mu); return rng(); } diff --git a/tensorflow/core/platform/s3/s3_file_system.cc b/tensorflow/core/platform/s3/s3_file_system.cc index 51c85592bf..234f3c3aed 100644 --- a/tensorflow/core/platform/s3/s3_file_system.cc +++ b/tensorflow/core/platform/s3/s3_file_system.cc @@ -38,7 +38,7 @@ static const size_t kS3ReadAppendableFileBufferSize = 1024 * 1024; static const int kS3GetChildrenMaxKeys = 100; Aws::Client::ClientConfiguration& GetDefaultClientConfig() { - static mutex cfg_lock; + static mutex cfg_lock(LINKER_INITIALIZED); static bool init(false); static Aws::Client::ClientConfiguration cfg; diff --git a/tensorflow/python/lib/core/py_func.cc b/tensorflow/python/lib/core/py_func.cc index b30125761f..8bf831f8ba 100644 --- a/tensorflow/python/lib/core/py_func.cc +++ b/tensorflow/python/lib/core/py_func.cc @@ -32,7 +32,7 @@ limitations under the License. namespace tensorflow { namespace { -static mutex mu; +static mutex mu(LINKER_INITIALIZED); static PyObject* py_trampoline GUARDED_BY(mu) = nullptr; // Returns the py_trampoline that is used to pass the control to the |