Commit b077851b authored by Nathan Bronson's avatar Nathan Bronson Committed by Facebook GitHub Bot

support VS2019 in UninitializedMemoryHacks, fix VS2017

Summary:
VS2019 changes the internal implementation of basic_string and vector.
This diff adds support for the new internals, and fixes a linkage
problem on VS2017.  It also adds the UninitializedMemoryHacksTest to
the getdeps-built tests.

For basic_string a single version handles both old and new.
basic_string::_Eos changed from public to private, so code that uses
the template specialization hack to invoke it when it is private will
work for the older public method as well.

vector does not have any suitable internal methods, so we need to adapt
to the new internal structure.

This diff fixes the issues addressed by
https://github.com/facebook/folly/pull/1345 , but uses an alternate
strategy to avoid reinterpret_cast.

Reviewed By: yfeldblum

Differential Revision: D20838799

fbshipit-source-id: eba7db2bd6feade1349d51be224c481a9156732b
parent a9d3606b
......@@ -745,8 +745,7 @@ if (BUILD_TESTS)
TEST ScopedEventBaseThreadTest SOURCES ScopedEventBaseThreadTest.cpp
TEST ssl_session_test
CONTENT_DIR certs/
SOURCES
SSLSessionTest.cpp
SOURCES SSLSessionTest.cpp
TEST writechain_test SOURCES WriteChainAsyncTransportWrapperTest.cpp
DIRECTORY io/async/ssl/test/
......@@ -765,6 +764,8 @@ if (BUILD_TESTS)
TEST thread_cached_arena_test WINDOWS_DISABLED
SOURCES ThreadCachedArenaTest.cpp
TEST mallctl_helper_test SOURCES MallctlHelperTest.cpp
TEST uninitialized_memory_hacks_test
SOURCES UninitializedMemoryHacksTest.cpp
DIRECTORY net/detail/test/
TEST socket_file_descriptor_map_test SOURCES SocketFileDescriptorMapTest.cpp
......
......@@ -243,19 +243,24 @@ struct MakeUnsafeStringSetLargerSize {
#elif defined(_MSC_VER)
// MSVC
template <typename Tag, typename T>
template <typename Tag, typename T, typename A, A Ptr_Eos>
struct MakeUnsafeStringSetLargerSize {
friend void unsafeStringSetLargerSizeImpl(
std::basic_string<T>& s,
std::size_t n) {
s._Eos(n);
// _Eos method is public for _MSC_VER <= 1916, private after
// s._Eos(n);
(s.*Ptr_Eos)(n);
}
};
#define FOLLY_DECLARE_STRING_RESIZE_WITHOUT_INIT(TYPE) \
template void std::basic_string<TYPE>::_Eos(std::size_t); \
template struct folly::detail::MakeUnsafeStringSetLargerSize< \
FollyMemoryDetailTranslationUnitTag, \
TYPE>; \
TYPE, \
void (std::basic_string<TYPE>::*)(std::size_t), \
&std::basic_string<TYPE>::_Eos>; \
FOLLY_DECLARE_STRING_RESIZE_WITHOUT_INIT_IMPL(TYPE)
#else
......@@ -360,14 +365,52 @@ struct MakeUnsafeVectorSetLargerSize : std::vector<T> {
&std::vector<TYPE>::_Vector_impl::_M_finish>; \
FOLLY_DECLARE_VECTOR_RESIZE_WITHOUT_INIT_IMPL(TYPE)
#elif defined(_MSC_VER)
// MSVC
#elif defined(_MSC_VER) && _MSC_VER <= 1916
// MSVC <= VS2017
template <typename Tag, typename T>
struct MakeUnsafeVectorSetLargerSize : std::vector<T> {
friend void unsafeVectorSetLargerSizeImpl(std::vector<T>& v, std::size_t n) {
v._Mylast() += (n - v.size());
}
};
#define FOLLY_DECLARE_VECTOR_RESIZE_WITHOUT_INIT(TYPE) \
template struct folly::detail::MakeUnsafeVectorSetLargerSize< \
FollyMemoryDetailTranslationUnitTag, \
TYPE>; \
FOLLY_DECLARE_VECTOR_RESIZE_WITHOUT_INIT_IMPL(TYPE)
#elif defined(_MSC_VER) && _MSC_VER > 1916
// MSVC >= VS2019
template <
typename Tag,
typename T,
typename A,
A Ptr_Mypair,
typename B,
B Ptr_Myval2,
typename C,
C Ptr_Mylast>
struct MakeUnsafeVectorSetLargerSize : std::vector<T> {
friend void unsafeVectorSetLargerSizeImpl(std::vector<T>& v, std::size_t n) {
// v._Mypair._Myval2._Mylast += (n - v.size());
((v.*Ptr_Mypair).*Ptr_Myval2).*Ptr_Mylast += (n - v.size());
}
};
#define FOLLY_DECLARE_VECTOR_RESIZE_WITHOUT_INIT(TYPE) \
extern inline void unsafeVectorSetLargerSizeImpl( \
std::vector<TYPE>& v, std::size_t n) { \
v._Mylast() += (n - v.size()); \
} \
#define FOLLY_DECLARE_VECTOR_RESIZE_WITHOUT_INIT(TYPE) \
template struct folly::detail::MakeUnsafeVectorSetLargerSize< \
FollyMemoryDetailTranslationUnitTag, \
TYPE, \
decltype(&std::vector<TYPE>::_Mypair), \
&std::vector<TYPE>::_Mypair, \
decltype(&decltype(std::declval<std::vector<TYPE>>()._Mypair)::_Myval2), \
&decltype(std::declval<std::vector<TYPE>>()._Mypair)::_Myval2, \
decltype(&decltype( \
std::declval<std::vector<TYPE>>()._Mypair._Myval2)::_Mylast), \
&decltype(std::declval<std::vector<TYPE>>()._Mypair._Myval2)::_Mylast>; \
FOLLY_DECLARE_VECTOR_RESIZE_WITHOUT_INIT_IMPL(TYPE)
#else
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment