-
Notifications
You must be signed in to change notification settings - Fork 974
LuaWrapper: Add support for std::variant
#16622
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Changes from all commits
0b52a46
c915437
1d17b0c
a34b21f
99d46e3
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -38,7 +38,6 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | |
| #include <list> | ||
| #include <map> | ||
| #include <memory> | ||
| #include <optional> | ||
| #include <random> | ||
| #include <set> | ||
| #include <stdexcept> | ||
|
|
@@ -56,6 +55,11 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | |
| #include <boost/type_traits.hpp> | ||
| #include <lua.hpp> | ||
|
|
||
| #if __cplusplus >= 201703L | ||
| #include <variant> | ||
| #include <optional> | ||
| #endif /* C++17 */ | ||
|
|
||
| // Set the older gcc define for tsan if clang or modern gcc tell us we have tsan. | ||
| #if defined(__has_feature) | ||
| #if __has_feature(thread_sanitizer) | ||
|
|
@@ -2001,8 +2005,10 @@ struct LuaContext::FunctionArgumentsCounter<> { | |
| // implementation of IsOptional | ||
| template<typename T> | ||
| struct LuaContext::IsOptional<boost::optional<T>> : public std::true_type {}; | ||
| #if __cplusplus >= 201703L | ||
| template<typename T> | ||
| struct LuaContext::IsOptional<std::optional<T>> : public std::true_type {}; | ||
| #endif /* C++ 17 */ | ||
|
|
||
| // implementation of LuaFunctionCaller | ||
| template<typename TFunctionType> | ||
|
|
@@ -2556,6 +2562,25 @@ struct LuaContext::Pusher<boost::variant<TTypes...>> | |
| }; | ||
| }; | ||
|
|
||
| #if __cplusplus >= 201703L | ||
| // std::variant | ||
| template<typename... TTypes> | ||
| struct LuaContext::Pusher<std::variant<TTypes...>> | ||
| { | ||
| static const int minSize = PusherMinSize<TTypes...>::size; | ||
| static const int maxSize = PusherMaxSize<TTypes...>::size; | ||
|
|
||
| static PushedObject push(lua_State* state, const std::variant<TTypes...>& value) noexcept { | ||
| PushedObject obj{state, 0}; | ||
| std::visit([&](auto&& arg) { | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. does this bump the luawrapper C++ requirement to C++17? Because in theory we try to stay in sync with upstream (which is me and I haven't spoken to any other users in years)
Member
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. It does,
Member
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Note that we added support for
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. oh, duh. I checked
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Right. No way back then. Do what feels good :)
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think it's good to keep in mind that this is possible if necessary, but I don't think we need to uglify the code with it now.
Member
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think we might get away with something like: template<class Type>
#if __cplusplus >= 201703L
using OptionalValue = std::optional<Type>;
#else
using OptionalValue = boost::optional<Type>;
#endif
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. ok, if it's that easy, why not :)
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. unless the caller uses
Member
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I pushed a commit fixing C++11 compatibility for now. |
||
| using T = std::decay_t<decltype(arg)>; | ||
| obj = Pusher<T>::push(state, arg); | ||
| }, value); | ||
| return obj; | ||
| } | ||
| }; | ||
| #endif /* C++17 */ | ||
|
|
||
| // boost::optional | ||
| template<typename TType> | ||
| struct LuaContext::Pusher<boost::optional<TType>> { | ||
|
|
@@ -2575,6 +2600,7 @@ struct LuaContext::Pusher<boost::optional<TType>> { | |
| } | ||
| }; | ||
|
|
||
| #if __cplusplus >= 201703L | ||
| // std::optional | ||
| template<typename TType> | ||
| struct LuaContext::Pusher<std::optional<TType>> { | ||
|
|
@@ -2593,6 +2619,7 @@ struct LuaContext::Pusher<std::optional<TType>> { | |
| } | ||
| } | ||
| }; | ||
| #endif /* C++17 */ | ||
|
|
||
| // tuple | ||
| template<typename... TTypes> | ||
|
|
@@ -2943,6 +2970,7 @@ struct LuaContext::Reader<boost::optional<TType>> | |
| } | ||
| }; | ||
|
|
||
| #if __cplusplus >= 201703L | ||
| // NOLINTBEGIN(clang-analyzer-cplusplus.NewDeleteLeaks) | ||
| template<typename TType> | ||
| struct LuaContext::Reader<std::optional<TType>> | ||
|
|
@@ -2960,8 +2988,9 @@ struct LuaContext::Reader<std::optional<TType>> | |
| } | ||
| }; | ||
| // NOLINTEND(clang-analyzer-cplusplus.NewDeleteLeaks) | ||
| #endif /* C++ 17 */ | ||
|
|
||
| // variant | ||
| // boost::variant | ||
| template<typename... TTypes> | ||
| struct LuaContext::Reader<boost::variant<TTypes...>> | ||
| { | ||
|
|
@@ -3008,6 +3037,42 @@ struct LuaContext::Reader<boost::variant<TTypes...>> | |
| } | ||
| }; | ||
|
|
||
| #if __cplusplus >= 201703L | ||
| // std::variant | ||
| template<typename... TTypes> | ||
| struct LuaContext::Reader<std::variant<TTypes...>> | ||
| { | ||
| using ReturnType = std::variant<TTypes...>; | ||
|
|
||
| private: | ||
| template<std::size_t I = 0> static boost::optional<ReturnType> variantRead(lua_State* state, int index) | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I see we do support
Member
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We could, but we need to convert all readers at the same time, so perhaps in a follow-up PR?
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. right, I feared something like that |
||
| { | ||
| constexpr auto nbTypes = std::variant_size_v<ReturnType>; | ||
| if constexpr (I >= nbTypes) { | ||
| return boost::none; | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. you can take the variant out of the boost but you can't take the boost out of the luawrapper ;) |
||
| } | ||
| using InitialType = std::variant_alternative_t<I, ReturnType>; | ||
| using DecayedType = std::decay_t<InitialType>; | ||
| if (const auto val = Reader<DecayedType>::read(state, index)) { | ||
| // we are using the initial, non-decayed type so that a | ||
| // cv-qualifiers are not ignored | ||
| return ReturnType{std::in_place_type<InitialType>, *val}; | ||
| } | ||
| if constexpr (I < (nbTypes - 1)) { | ||
| return variantRead<I + 1>(state, index); | ||
| } | ||
| return boost::none; | ||
| } | ||
|
|
||
| public: | ||
| static auto read(lua_State* state, int index) | ||
| -> boost::optional<ReturnType> | ||
| { | ||
| return variantRead(state, index); | ||
| } | ||
| }; | ||
| #endif /* C++ 17 */ | ||
|
|
||
| // reading a tuple | ||
| // tuple have an additional argument for their functions, that is the maximum size to read | ||
| // if maxSize is smaller than the tuple size, then the remaining parameters will be left to default value | ||
|
|
||
Uh oh!
There was an error while loading. Please reload this page.