Compare commits

...

2 Commits
main ... 3.14.x

Author SHA1 Message Date
Biswapriyo Nath
19fb89416f stubs/mutex: Fix compilation by initializing variable in WrappedMutex class.
This solves the following error in gcc:
explicitly defaulted function cannot be declared 'constexpr' because the implicit declaration is not 'constexpr'
2021-01-13 10:13:07 -08:00
Adam Cozzette
4a09d77a85 Remove PROTOBUF_MAYBE_CONSTEXPR and make the constructor constexpr even in MSVC
This solves a conflict when using Clang for Windows.

This is just a cherry-pick of the internal change cl/341698875.
2020-12-04 14:03:37 -08:00
4 changed files with 30 additions and 20 deletions

View File

@ -329,7 +329,7 @@ class PROTOBUF_EXPORT MapFieldBase {
// It uses a linker initialized mutex, so it is not compatible with regular
// runtime instances.
// Except in MSVC, where we can't have a constinit mutex.
explicit PROTOBUF_MAYBE_CONSTEXPR MapFieldBase(ConstantInitialized)
explicit constexpr MapFieldBase(ConstantInitialized)
: arena_(nullptr),
repeated_field_(nullptr),
mutex_(GOOGLE_PROTOBUF_LINKER_INITIALIZED),

View File

@ -148,9 +148,6 @@
#ifdef PROTOBUF_CONSTINIT
#error PROTOBUF_CONSTINIT was previously defined
#endif
#ifdef PROTOBUF_MAYBE_CONSTEXPR
#error PROTOBUF_MAYBE_CONSTEXPR was previously defined
#endif
#ifdef PROTOBUF_ATTRIBUTE_NO_DESTROY
#error PROTOBUF_ATTRIBUTE_NO_DESTROY was previously defined
#endif
@ -560,15 +557,6 @@
#define PROTOBUF_CONSTINIT
#endif
// Some constructors can't be constexpr under MSVC, but given that MSVC will not
// do constant initialization of globals anyway we can omit `constexpr` from
// them. These constructors are marked with PROTOBUF_MAYBE_CONSTEXPR
#if defined(_MSC_VER)
#define PROTOBUF_MAYBE_CONSTEXPR
#else
#define PROTOBUF_MAYBE_CONSTEXPR constexpr
#endif
#if _MSC_VER
#define PROTOBUF_DISABLE_MSVC_UNION_WARNING \
__pragma(warning(push)) \

View File

@ -75,7 +75,6 @@
#undef PROTOBUF_DISABLE_MSVC_UNION_WARNING
#undef PROTOBUF_ENABLE_MSVC_UNION_WARNING
#undef PROTOBUF_CONSTINIT
#undef PROTOBUF_MAYBE_CONSTEXPR
#undef PROTOBUF_ATTRIBUTE_NO_DESTROY
// Restore macro that may have been #undef'd in port_def.inc.

View File

@ -90,12 +90,33 @@ class PROTOBUF_EXPORT CriticalSectionLock {
#endif
// In MSVC std::mutex does not have a constexpr constructor.
// This wrapper makes the constructor constexpr.
template <typename T>
class CallOnceInitializedMutex {
public:
constexpr CallOnceInitializedMutex() : flag_{}, buf_{} {}
~CallOnceInitializedMutex() { get().~T(); }
void lock() { get().lock(); }
void unlock() { get().unlock(); }
private:
T& get() {
std::call_once(flag_, [&] { ::new (static_cast<void*>(&buf_)) T(); });
return reinterpret_cast<T&>(buf_);
}
std::once_flag flag_;
alignas(T) char buf_[sizeof(T)];
};
// Mutex is a natural type to wrap. As both google and other organization have
// specialized mutexes. gRPC also provides an injection mechanism for custom
// mutexes.
class GOOGLE_PROTOBUF_CAPABILITY("mutex") PROTOBUF_EXPORT WrappedMutex {
public:
WrappedMutex() = default;
constexpr WrappedMutex() = default;
void Lock() GOOGLE_PROTOBUF_ACQUIRE() { mu_.lock(); }
void Unlock() GOOGLE_PROTOBUF_RELEASE() { mu_.unlock(); }
// Crash if this Mutex is not held exclusively by this thread.
@ -103,11 +124,13 @@ class GOOGLE_PROTOBUF_CAPABILITY("mutex") PROTOBUF_EXPORT WrappedMutex {
void AssertHeld() const {}
private:
#ifndef GOOGLE_PROTOBUF_SUPPORT_WINDOWS_XP
std::mutex mu_;
#else // ifndef GOOGLE_PROTOBUF_SUPPORT_WINDOWS_XP
CriticalSectionLock mu_;
#endif // #ifndef GOOGLE_PROTOBUF_SUPPORT_WINDOWS_XP
#if defined(GOOGLE_PROTOBUF_SUPPORT_WINDOWS_XP)
CallOnceInitializedMutex<CriticalSectionLock> mu_ {};
#elif defined(_MSC_VER)
CallOnceInitializedMutex<std::mutex> mu_ {};
#else
std::mutex mu_ {};
#endif
};
using Mutex = WrappedMutex;