GCC+TSan error
Compiling Asio with GCC+TSan gives me the following error:
In function 'void std::atomic_thread_fence(memory_order)',
inlined from 'boost::asio::detail::std_fenced_block::std_fenced_block(full_t)' at ./boost/asio/detail/std_fenced_block.hpp:46:29:
/usr/include/c++/12/bits/atomic_base.h:133:26: error: 'atomic_thread_fence' is not supported with '-fsanitize=thread' [-Werror=tsan]
133 | { __atomic_thread_fence(int(__m)); }
| ~~~~~~~~~~~~~~~~~~~~~^~~~~~~~~~
In function 'void std::atomic_thread_fence(memory_order)',
inlined from 'boost::asio::detail::std_fenced_block::~std_fenced_block()' at ./boost/asio/detail/std_fenced_block.hpp:52:29:
/usr/include/c++/12/bits/atomic_base.h:133:26: error: 'atomic_thread_fence' is not supported with '-fsanitize=thread' [-Werror=tsan]
133 | { __atomic_thread_fence(int(__m)); }
| ~~~~~~~~~~~~~~~~~~~~~^~~~~~~~~~
cc1plus: all warnings being treated as errors
Because TSan does not support atomic_thread_fence.
LLVM's https://github.com/llvm/llvm-project/blob/ad1161f9b5ff251b80788033e4db82b5a11b187b/compiler-rt/include/sanitizer/tsan_interface.h#L24-L25 can be used instead.
I'm not sure there's anything actionable about this but I'm just reporting it.
I've also noticed BOOST_ASIO_DISABLE_FENCED_BLOCK is there. I imagine disabling the fenced block takes care of the GCC warning, but if these fences are really necessary, TSan will report data races.
There is any news on this? Thanks
I could open a PR with a patch that looks something like this below. I've only tested it so far with gcc14 on Linux x86_64, but it makes TSAN happy in my code that uses the boost version of this.
diff --git a/include/asio/detail/std_fenced_block.hpp b/include/asio/detail/std_fenced_block.hpp
index 2d79656be..cf8619d04 100644
--- a/include/asio/detail/std_fenced_block.hpp
+++ b/include/asio/detail/std_fenced_block.hpp
@@ -21,6 +21,17 @@
#include "asio/detail/push_options.hpp"
+#if defined(__has_feature)
+# if __has_feature(thread_sanitizer)
+# include "sanitizer/tsan_interface.h"
+# define USE_TSAN_SEMANTICS 1
+# else
+# define USE_TSAN_SEMANTICS 0
+# endif
+#else
+# define USE_TSAN_SEMANTICS 0
+#endif
+
namespace asio {
namespace detail {
@@ -39,14 +50,27 @@ public:
// Constructor for a full fenced block.
explicit std_fenced_block(full_t)
{
+#if USE_TSAN_SEMANTICS
+ __tsan_acquire(&tsan);
+#else
std::atomic_thread_fence(std::memory_order_acquire);
+#endif
}
// Destructor.
~std_fenced_block()
{
+#if USE_TSAN_SEMANTICS
+ __tsan_release(&tsan);
+#else
std::atomic_thread_fence(std::memory_order_release);
+#endif
}
+
+#if USE_TSAN_SEMANTICS
+private:
+ int tsan;
+#endif
};
} // namespace detail