Compare commits

...

3 Commits

2 changed files with 26 additions and 2 deletions

View File

@ -587,8 +587,21 @@ using string_view = basic_string_view<char>;
template <typename T> class basic_appender;
using appender = basic_appender<char>;
namespace detail {
// Checks whether T is a container with contiguous storage.
template <typename T> struct is_contiguous : std::false_type {};
template <typename T>
auto is_contiguous_helper(int)
-> decltype(std::declval<T&>().data(), std::declval<T&>().size(),
std::declval<T&>().resize(size_t{}),
std::declval<T&>()[size_t{}], std::true_type{});
template <typename T> auto is_contiguous_helper(...) -> std::false_type;
} // namespace detail
template <typename T>
struct is_contiguous : decltype(detail::is_contiguous_helper<T>(0)) {};
class context;
template <typename OutputIt, typename Char> class generic_context;

View File

@ -8,6 +8,11 @@
#ifndef FMT_FORMAT_INL_H_
#define FMT_FORMAT_INL_H_
#ifdef __SANITIZE_THREAD__
extern "C" void __tsan_acquire(void*);
extern "C" void __tsan_release(void*);
#endif
#ifndef FMT_MODULE
# include <stddef.h> // ptrdiff_t
@ -1696,6 +1701,9 @@ class file_print_buffer<F, enable_if_t<has_flockfile<F>::value>>
public:
explicit file_print_buffer(F* f) : buffer(grow, size_t()), file_(f) {
flockfile(f);
#ifdef __SANITIZE_THREAD__
__tsan_acquire(f);
#endif
file_.init_buffer();
auto buf = file_.get_write_buffer();
set(buf.data, buf.size);
@ -1703,7 +1711,10 @@ class file_print_buffer<F, enable_if_t<has_flockfile<F>::value>>
~file_print_buffer() {
file_.advance_write_buffer(size());
bool flush = file_.needs_flush();
F* f = file_; // Make funlockfile depend on the template parameter F
F* f = file_; // Make funlockfile depend on the template parameter F.
#ifdef __SANITIZE_THREAD__
__tsan_release(f);
#endif
funlockfile(f); // for the system API detection to work.
if (flush) fflush(file_);
}