ThePhD / sol2

Sol3 (sol2 v3.0) - a C++ <-> Lua API wrapper with advanced features and top notch performance - is here, and it's great! Documentation:
http://sol2.rtfd.io/
MIT License
4.12k stars 500 forks source link

Compiles with sol 3.3.0 working only in debug mode while release builds break. #1459

Open McKillroy opened 1 year ago

McKillroy commented 1 year ago

I had a project resting for a while and am picking it up again and I now have broken builds in release mode while debug builds still work. I tried using older versions of sol but it didn't change. Ofc there were some changes in the codebase - e.g. using C++20 now. I am not sure I'm able to produce a minimal example shortly, so I'm just providing the error message here, maybe it's sufficient for people in the know of the sol2 intestines .

Error message:

[19/21] Building CXX object src\sim\CMakeFiles\sim.dir\__\luaengine\luae_engine.cpp.obj
  FAILED: src/sim/CMakeFiles/sim.dir/__/luaengine/luae_engine.cpp.obj 
  C:\PROGRA~1\MIB055~1\2022\COMMUN~1\VC\Tools\MSVC\1435~1.322\bin\Hostx64\x64\cl.exe  /nologo /TP -DUSE_JEMALLOC=0 -DUSE_MIMALLOC=1 -DBOOST_ALL_NO_LIB -DFMT_SHARED -DHPX_APPLICATION_EXPORTS -DHPX_APPLICATION_NAME=sim -DHPX_APPLICATION_NAME_DEFAULT=sim -DHPX_APPLICATION_STRING=\"sim\" -DHPX_HAVE_CXX17_STD_VARIANT=USE_STD_VARIANT -DHPX_PREFIX_DEFAULT=\".../build/RelWithDebInfo/vcpkg_installed/x64-windows/share/hpx/../..\" -DLUA_BUILD_AS_DLL -DSOL_ALL_SAFETIES_ON=0 -DSOL_EXCEPTIONS_SAFE_PROPAGATION=0 -DSOL_PRINT_ERRORS=0 -DSOL_USING_CXX_LUA=1 -IC:\src -external:IC:\..\build\..\include -external:W0 /permissive- /EHsc /Zi /O2 /Ob1 /DNDEBUG -MD -Ox -Ob1 -d2Zi+ -Zc:inline -Gw -Zo -Zc:throwingNew -Zc:rvalueCast -Zc:strictStrings -Zc:__cplusplus -GR -MP -bigobj -permissive- -std:c++17 /showIncludes /Fosrc\sim\CMakeFiles\sim.dir\__\luaengine\luae_engine.cpp.obj /Fdsrc\sim\CMakeFiles\sim.dir\ /FS -c C:\src\luaengine\luae_engine.cpp
C:\..\build\..\include\sol\usertype_container.hpp(541): error C2440: 'return': cannot convert from 'std::string' to 'std::string &'
  C:\..\build\..\include\sol/usertype_container.hpp(541): note: A non-const reference may only be bound to an lvalue
  C:\..\build\..\include\sol/usertype_container.hpp(527): note: while compiling class template member function 'std::string &sol::container_detail::usertype_container_default<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>,void>::get_src(lua_State *)'
  C:\..\build\..\include\sol/usertype_container.hpp(1559): note: see reference to class template instantiation 'sol::container_detail::usertype_container_default<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>,void>' being compiled
  C:\..\build\..\include\sol/usertype_container.hpp(235): note: see reference to class template instantiation 'sol::usertype_container<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>>' being compiled
  C:\..\build\..\include\sol/usertype_container_launch.hpp(133): note: see reference to class template instantiation 'sol::container_detail::has_traits_pairs_test<sol::usertype_container<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>>>' being compiled
  C:\..\build\..\include\sol/usertype_container_launch.hpp(133): note: see reference to alias template instantiation 'sol::container_detail::has_traits_pairs<sol::usertype_container<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>>>' being compiled
  C:\..\build\..\include\sol/usertype_container_launch.hpp(132): note: while compiling class template member function 'int sol::container_detail::u_c_launch<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>>::real_pairs_call(lua_State *)'
  C:\..\build\..\include\sol/usertype_core.hpp(126): note: see reference to class template instantiation 'sol::container_detail::u_c_launch<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>>' being compiled
  C:\..\build\..\include\sol/stack_push.hpp(258): note: see reference to function template instantiation 'void sol::detail::insert_default_registrations<std::basic_string<char,std::char_traits<char>,std::allocator<char>>,sol::detail::indexed_insert&,bool(__cdecl &)(sol::meta_function)>(IFx,Fx)' being compiled
          with
          [
              IFx=sol::detail::indexed_insert &,
              Fx=bool (__cdecl &)(sol::meta_function)
          ]
  C:\..\build\..\include\sol/stack_push.hpp(245): note: see reference to function template instantiation 'int sol::stack::stack_detail::uu_pusher<T>::push_deep<const _First&>(lua_State *,const _First &)' being compiled
          with
          [
              T=Tu,
              _First=std::shared_ptr<std::string>
          ]
  C:\..\build\..\include\sol/stack_push.hpp(250): note: see reference to function template instantiation 'int sol::stack::stack_detail::uu_pusher<T>::push_deep<const _First&>(lua_State *,const _First &)' being compiled
          with
          [
              T=Tu,
              _First=std::shared_ptr<std::string>
          ]
  C:\..\build\..\include\sol/stack_push.hpp(287): note: see reference to function template instantiation 'int sol::stack::stack_detail::uu_pusher<T>::push<const _First&,>(lua_State *,Arg)' being compiled
          with
          [
              T=Tu,
              _First=std::shared_ptr<std::string>,
              Arg=const std::shared_ptr<std::string> &
          ]
  C:\..\build\..\include\sol/stack_push.hpp(290): note: see reference to function template instantiation 'int sol::stack::stack_detail::uu_pusher<T>::push<const _First&,>(lua_State *,Arg)' being compiled
          with
          [
              T=Tu,
              _First=std::shared_ptr<std::string>,
              Arg=const std::shared_ptr<std::string> &
          ]
  C:\..\build\..\include\sol/stack_core.hpp(884): note: see reference to function template instantiation 'int sol::stack::unqualified_pusher<Tu,void>::push<const _First&>(lua_State *,const _First &)' being compiled
          with
          [
              _First=std::shared_ptr<std::string>
          ]
  C:\..\build\..\include\sol/stack_core.hpp(897): note: see reference to function template instantiation 'int sol::stack::unqualified_pusher<Tu,void>::push<const _First&>(lua_State *,const _First &)' being compiled
          with
          [
              _First=std::shared_ptr<std::string>
          ]
  C:\..\build\..\include\sol/stack_push.hpp(297): note: see reference to function template instantiation 'int sol::stack::push<sol::detail::as_unique_tag<T>,const _First&,,void>(lua_State *,Arg)' being compiled
          with
          [
              T=Tu,
              _First=std::shared_ptr<std::string>,
              Arg=const std::shared_ptr<std::string> &
          ]
  C:\..\build\..\include\sol/stack_core.hpp(865): note: see reference to function template instantiation 'int sol::stack::unqualified_pusher<Tu,void>::push<const _First&>(lua_State *,const _First &)' being compiled
          with
          [
              _First=std::shared_ptr<std::string>
          ]
  C:\..\build\..\include\sol/stack_core.hpp(878): note: see reference to function template instantiation 'int sol::stack::unqualified_pusher<Tu,void>::push<const _First&>(lua_State *,const _First &)' being compiled
          with
          [
              _First=std::shared_ptr<std::string>
          ]
  C:\..\build\..\include\sol/stack_push.hpp(1366): note: see reference to function template instantiation 'int sol::stack::push<const std::shared_ptr<std::string>&,>(lua_State *,T)' being compiled
          with
          [
              T=const std::shared_ptr<std::string> &
          ]
  C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Tools\MSVC\14.35.32215\include\type_traits(1572): note: see reference to function template instantiation 'int sol::stack::stack_detail::push_function::operator ()<const std::shared_ptr<std::string>&>(T) const' being compiled
          with
          [
              T=const std::shared_ptr<std::string> &
          ]
  C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Tools\MSVC\14.35.32215\include\variant(1445): note: see reference to function template instantiation 'int std::invoke<_Callable,const std::shared_ptr<std::string>&,>(_Callable &&,_Ty1) noexcept(false)' being compiled
          with
          [
              _Callable=sol::stack::stack_detail::push_function,
              _Ty1=const std::shared_ptr<std::string> &
          ]
  C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Tools\MSVC\14.35.32215\include\variant(1534): note: see reference to function template instantiation '_Ret std::_Variant_dispatcher<_Indices>::_Dispatch2<_Ret,sol::stack::stack_detail::push_function,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type>&,false>(_Callable &&,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type> &)' being compiled
          with
          [
              _Ret=_Ret,
              _Callable=sol::stack::stack_detail::push_function
          ]
  C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Tools\MSVC\14.35.32215\include\variant(1536): note: see reference to function template instantiation '_Ret std::_Variant_dispatcher<_Indices>::_Dispatch2<_Ret,sol::stack::stack_detail::push_function,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type>&,false>(_Callable &&,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type> &)' being compiled
          with
          [
              _Ret=_Ret,
              _Callable=sol::stack::stack_detail::push_function
          ]
  C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Tools\MSVC\14.35.32215\include\variant(1574): note: see reference to function template instantiation '_Ret std::_Visit_strategy<2>::_Visit2<_Ret,_ListOfIndexVectors,sol::stack::stack_detail::push_function,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type>&>(size_t,_Callable &&,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type> &)' being compiled
          with
          [
              _Ret=_Ret,
              _Callable=sol::stack::stack_detail::push_function
          ]
  C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Tools\MSVC\14.35.32215\include\variant(1614): note: see reference to function template instantiation '_Ret std::_Visit_impl<5,_Ret,_ListOfIndexVectors,sol::stack::stack_detail::push_function,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type>&>(_Callable &&,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type> &)' being compiled
          with
          [
              _Ret=_Ret,
              _Callable=sol::stack::stack_detail::push_function
          ]
  C:\..\build\..\include\sol/stack_push.hpp(1375): note: see reference to function template instantiation 'int std::visit<sol::stack::stack_detail::push_function,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type>&,void>(_Callable &&,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type> &)' being compiled
          with
          [
              _Callable=sol::stack::stack_detail::push_function
          ]
  C:\..\build\..\include\sol/stack_push.hpp(1375): note: while compiling class template member function 'int sol::stack::unqualified_pusher<Tu,void>::push(lua_State *,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type> &)'
  C:\..\build\..\include\sol/stack_core.hpp(897): note: see reference to function template instantiation 'int sol::stack::unqualified_pusher<Tu,void>::push(lua_State *,const std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type> &)' being compiled
  C:\..\build\..\include\sol/stack_core.hpp(884): note: see reference to class template instantiation 'sol::stack::unqualified_pusher<Tu,void>' being compiled
  C:\..\build\..\include\sol/stack_core.hpp(922): note: see reference to function template instantiation 'int sol::stack::push<Tr,std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type>&,,void>(lua_State *,Arg)' being compiled
          with
          [
              Arg=std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type> &
          ]
  C:\..\build\..\include\sol/usertype_container.hpp(587): note: see reference to function template instantiation 'int sol::stack::stack_detail::push_reference<std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type>&,std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type>&,>(lua_State *,Arg)' being compiled
          with
          [
              Arg=std::variant<int64_t,double,std::shared_ptr<std::string>,hpx::id_type> &
          ]
  C:\..\build\..\include\sol/usertype_container.hpp(572): note: see reference to function template instantiation 'sol::detail::error_result sol::container_detail::usertype_container_default<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>,void>::get_associative<_InIt>(std::false_type,lua_State *,Iter &)' being compiled
          with
          [
              _InIt=std::_Vector_iterator<std::_Vector_val<std::_Simple_types<agns::messaging::vardata>>>,
              Iter=std::_Vector_iterator<std::_Vector_val<std::_Simple_types<agns::messaging::vardata>>>
          ]
  C:\..\build\..\include\sol/usertype_container.hpp(572): note: see reference to function template instantiation 'sol::detail::error_result sol::container_detail::usertype_container_default<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>,void>::get_associative<_InIt>(std::false_type,lua_State *,Iter &)' being compiled
          with
          [
              _InIt=std::_Vector_iterator<std::_Vector_val<std::_Simple_types<agns::messaging::vardata>>>,
              Iter=std::_Vector_iterator<std::_Vector_val<std::_Simple_types<agns::messaging::vardata>>>
          ]
  C:\..\build\..\include\sol/usertype_container.hpp(565): note: while compiling class template member function 'sol::detail::error_result sol::container_detail::usertype_container_default<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>,void>::at_category(std::random_access_iterator_tag,lua_State *,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> &,ptrdiff_t)'
  C:\..\build\..\include\sol/usertype_container.hpp(576): note: see reference to function template instantiation 'sol::detail::error_result sol::container_detail::usertype_container_default<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>,void>::at_category(std::random_access_iterator_tag,lua_State *,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> &,ptrdiff_t)' being compiled
  C:\..\build\..\include\sol/usertype_container.hpp(1559): note: see reference to class template instantiation 'sol::container_detail::usertype_container_default<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>,void>' being compiled
  C:\..\build\..\include\sol/usertype_container.hpp(139): note: see reference to class template instantiation 'sol::usertype_container<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>>' being compiled
  C:\..\build\..\include\sol/usertype_container_launch.hpp(245): note: see reference to class template instantiation 'sol::container_detail::has_traits_index_of_test<sol::usertype_container<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>>>' being compiled
  C:\..\build\..\include\sol/usertype_container_launch.hpp(245): note: see reference to alias template instantiation 'sol::container_detail::has_traits_index_of<sol::usertype_container<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>>>' being compiled
  C:\..\build\..\include\sol/usertype_container_launch.hpp(244): note: while compiling class template member function 'int sol::container_detail::u_c_launch<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>>::real_index_of_call(lua_State *)'
  C:\..\build\..\include\sol/usertype_container_launch.hpp(335): note: see reference to class template instantiation 'sol::container_detail::u_c_launch<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>>' being compiled
  C:\..\build\..\include\sol/usertype_container_launch.hpp(328): note: while compiling class template member function 'void sol::stack::stack_detail::metatable_setup<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> *,false>::operator ()(void)'
  C:\..\build\..\include\sol/stack_push.hpp(207): note: see reference to function template instantiation 'void sol::stack::stack_detail::metatable_setup<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> *,false>::operator ()(void)' being compiled
  C:\..\build\..\include\sol/usertype_container_launch.hpp(424): note: see reference to class template instantiation 'sol::stack::stack_detail::metatable_setup<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> *,false>' being compiled
  C:\..\build\..\include\sol/usertype_container_launch.hpp(423): note: while compiling class template member function 'int sol::stack::unqualified_pusher<Tu,void>::push(lua_State *,T *)'
          with
          [
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>
          ]
  C:\..\build\..\include\sol/stack_core.hpp(878): note: see reference to function template instantiation 'int sol::stack::unqualified_pusher<Tu,void>::push(lua_State *,T *)' being compiled
          with
          [
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>
          ]
  C:\..\build\..\include\sol/stack_core.hpp(865): note: see reference to class template instantiation 'sol::stack::unqualified_pusher<Tu,void>' being compiled
  C:\..\build\..\include\sol/stack_push.hpp(233): note: see reference to function template instantiation 'int sol::stack::push<T*,>(lua_State *,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> *&&)' being compiled
          with
          [
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>
          ]
  C:\..\build\..\include\sol/stack_core.hpp(884): note: see reference to function template instantiation 'int sol::stack::unqualified_pusher<sol::detail::as_reference_tag,void>::push<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>&>(lua_State *,T)' being compiled
          with
          [
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> &
          ]
  C:\..\build\..\include\sol/stack_core.hpp(922): note: see reference to function template instantiation 'int sol::stack::push<Tr,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>&,,void>(lua_State *,Arg)' being compiled
          with
          [
              Arg=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> &
          ]
  C:\..\build\..\include\sol/stack_core.hpp(942): note: see reference to function template instantiation 'int sol::stack::stack_detail::push_reference<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>&,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>&,>(lua_State *,Arg)' being compiled
          with
          [
              Arg=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> &
          ]
  C:\..\build\..\include\sol/stack.hpp(266): note: see reference to function template instantiation 'int sol::stack::push_reference<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>&,>(lua_State *,T)' being compiled
          with
          [
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> &
          ]
  C:\..\build\..\include\sol/call.hpp(475): note: see reference to function template instantiation 'int sol::stack::call_into_lua<false,true,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>,,,caller,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* &,object_type&>(sol::types<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>>,sol::types<>,lua_State *,int,Fx &&,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* &,object_type &)' being compiled
          with
          [
              Fx=caller
          ]
  C:\..\build\..\include\sol/call.hpp(475): note: see reference to function template instantiation 'int sol::call_detail::lua_call_wrapper<T,uFx,true,true,false,0,true,void>::call<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* &,object_type&>(lua_State *,Fx,object_type &)' being compiled
          with
          [
              T=agns::messaging::TestMessage,
              Fx=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* &
          ]
  C:\..\build\..\include\sol/call.hpp(530): note: see reference to function template instantiation 'int sol::call_detail::lua_call_wrapper<T,uFx,true,true,false,0,true,void>::call<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* &,object_type&>(lua_State *,Fx,object_type &)' being compiled
          with
          [
              T=agns::messaging::TestMessage,
              Fx=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* &
          ]
  C:\..\build\..\include\sol/call.hpp(898): note: see reference to function template instantiation 'int sol::call_detail::lua_call_wrapper<T,uFx,true,true,false,0,true,void>::call<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* &,>(lua_State *,Fx)' being compiled
          with
          [
              T=agns::messaging::TestMessage,
              Fx=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* &
          ]
  C:\..\build\..\include\sol/call.hpp(907): note: see reference to function template instantiation 'int sol::call_detail::lua_call_wrapper<T,uFx,true,true,false,0,true,void>::call<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* &,>(lua_State *,Fx)' being compiled
          with
          [
              T=agns::messaging::TestMessage,
              Fx=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* &
          ]
  C:\..\build\..\include\sol/usertype_storage.hpp(90): note: see reference to function template instantiation 'int sol::call_detail::call_wrapped<T,true,true,0,false,true,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* &,>(lua_State *,Fx)' being compiled
          with
          [
              T=agns::messaging::TestMessage,
              Fx=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* &
          ]
  C:\..\build\..\include\sol/usertype_storage.hpp(667): note: see reference to function template instantiation 'int sol::u_detail::binding<KeyU,ValueU,T>::call_with_<true,true>(lua_State *,void *)' being compiled
          with
          [
              T=agns::messaging::TestMessage
          ]
  C:\..\build\..\include\sol/usertype_storage.hpp(721): note: see reference to function template instantiation 'int sol::u_detail::binding<KeyU,ValueU,T>::call_with_<true,true>(lua_State *,void *)' being compiled
          with
          [
              T=agns::messaging::TestMessage
          ]
  C:\..\build\..\include\sol/usertype_storage.hpp(804): note: see reference to function template instantiation 'void sol::u_detail::usertype_storage_base::set<T,_Ty,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* >(lua_State *,Key &&,Value &&)' being compiled
          with
          [
              T=agns::messaging::TestMessage,
              _Ty=const char *,
              Key=const char *,
              Value=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\..\build\..\include\sol/usertype.hpp(90): note: see reference to function template instantiation 'void sol::u_detail::usertype_storage<T>::set<_Ty,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* >(lua_State *,Key &&,Value &&)' being compiled
          with
          [
              T=agns::messaging::TestMessage,
              _Ty=const char *,
              Key=const char *,
              Value=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\..\build\..\include\sol/usertype.hpp(90): note: see reference to function template instantiation 'void sol::u_detail::usertype_storage<T>::set<_Ty,std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* >(lua_State *,Key &&,Value &&)' being compiled
          with
          [
              T=agns::messaging::TestMessage,
              _Ty=const char *,
              Key=const char *,
              Value=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\..\build\..\include\sol/usertype_proxy.hpp(59): note: see reference to function template instantiation 'sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &sol::basic_usertype<agns::messaging::TestMessage,sol::reference>::set<const char*,_Ty>(Key &&,Value &&)' being compiled
          with
          [
              _Ty=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* ,
              Key=const char *,
              Value=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\..\build\..\include\sol/usertype_proxy.hpp(64): note: see reference to function template instantiation 'sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &sol::basic_usertype<agns::messaging::TestMessage,sol::reference>::set<const char*,_Ty>(Key &&,Value &&)' being compiled
          with
          [
              _Ty=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* ,
              Key=const char *,
              Value=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\..\build\..\include\sol/usertype_proxy.hpp(86): note: see reference to function template instantiation 'void sol::usertype_proxy<sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &,const char *>::tuple_set<0,_Ty>(std::integer_sequence<size_t,0>,T &&) &&' being compiled
          with
          [
              _Ty=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* ,
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\..\build\..\include\sol/usertype_proxy.hpp(86): note: see reference to function template instantiation 'void sol::usertype_proxy<sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &,const char *>::tuple_set<0,_Ty>(std::integer_sequence<size_t,0>,T &&) &&' being compiled
          with
          [
              _Ty=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* ,
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\..\build\..\include\sol/usertype_proxy.hpp(97): note: see reference to function template instantiation 'sol::usertype_proxy<sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &,const char *> &&sol::usertype_proxy<sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &,const char *>::set<_Ty>(T &&) &&' being compiled
          with
          [
              _Ty=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* ,
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\..\build\..\include\sol/usertype_proxy.hpp(97): note: see reference to function template instantiation 'sol::usertype_proxy<sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &,const char *> &&sol::usertype_proxy<sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &,const char *>::set<_Ty>(T &&) &&' being compiled
          with
          [
              _Ty=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* ,
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\src\luaengine\luae_init_messaging.hpp(109): note: see reference to function template instantiation 'sol::usertype_proxy<sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &,const char *> &&sol::usertype_proxy<sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &,const char *>::operator =<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* >(T &&) &&' being compiled
          with
          [
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\src\luaengine\luae_init_messaging.hpp(109): note: see reference to function template instantiation 'sol::usertype_proxy<sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &,const char *> &&sol::usertype_proxy<sol::basic_usertype<agns::messaging::TestMessage,sol::reference> &,const char *>::operator =<std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>>agns::messaging::object_message_base::* >(T &&) &&' being compiled
          with
          [
              T=std::vector<agns::messaging::vardata,mi_stl_allocator<agns::messaging::vardata>> agns::messaging::object_message_base::* 
          ]
  C:\..\build\..\include\sol/usertype_container.hpp(1368): note: see reference to function template instantiation 'int sol::container_detail::usertype_container_default<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>,void>::pairs_associative<false>(std::false_type,lua_State *)' being compiled
  C:\..\build\..\include\sol/usertype_container.hpp(1368): note: see reference to function template instantiation 'int sol::container_detail::usertype_container_default<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>,void>::pairs_associative<false>(std::false_type,lua_State *)' being compiled
  C:\..\build\..\include\sol/usertype_container.hpp(1366): note: while compiling class template member function 'int sol::container_detail::usertype_container_default<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>,void>::pairs(lua_State *)'
  C:\..\build\..\include\sol/usertype_container_launch.hpp(125): note: see reference to function template instantiation 'int sol::container_detail::usertype_container_default<sol::as_container_t<std::basic_string<char,std::char_traits<char>,std::allocator<char>>>,void>::pairs(lua_State *)' being compiled
C:\..\build\..\include\sol\usertype_container.hpp(543): error C7683: you cannot create a reference to 'void'
C:\..\build\..\include\sol\usertype_container.hpp(543): error C3313: 'return expression': variable cannot have the type 'auto &'
C:\..\build\..\include\sol\usertype_container.hpp(543): error C3487: 'int': all return expressions must deduce to the same type: previously it was 'std::string &'
  ninja: build stopped: subcommand failed.
Install succeeded.
McKillroy commented 1 year ago

I isolated the error in my vcode (used to work flawlessly in the past):

/// This first part works
auto eventtype_test_table = solstate_.new_usertype<TestMessage>(
        "TestEvent",
        sol::factories( &MessageFactory<TestMessage> )
);
/// This part breaks with the error message above (Only in release mode sol 2.3.2, C++20, MSVC latest)
eventtype_test_table[ "arg" ] = &TestMessage::args;
McKillroy commented 1 year ago

It seems my build works again in release mode with SOL_SAFE_USERTYPE=1 which leaves me with one question: Do the various SOL safeties have any runtime performance penalty or are they just about compilation times?

Rochet2 commented 1 year ago

Do the various SOL safeties have any runtime performance penalty or are they just about compilation times?

Some of them are definitely introducing runtime overhead. For example, normally a double value would be cast into an integer, but some safeties (SOL_SAFE_NUMERICS ?) introduce checks that make sure the number is an integer instead of a float like 0.5. Doing so introduces a lot of overhead for operations that use numbers. Casting is (obviously?) a lot faster than running several functions that check some constraints.

For SOL_SAFE_USERTYPE specifically, if you search it in the codebase you can see for example this part which introduces a stack check which is overhead compared to not doing it. Overall seems like most changes related to the setting are similar. Just a check-get instead of plain get, followed by code that does a few IF checks on the value to determine if it is nil.

McKillroy commented 1 year ago

Do the various SOL safeties have any runtime performance penalty or are they just about compilation times?

Some of them are definitely introducing runtime overhead. For example, normally a double value would be cast into an integer, but some safeties (SOL_SAFE_NUMERICS ?) introduce checks that make sure the number is an integer instead of a float like 0.5. Doing so introduces a lot of overhead for operations that use numbers. Casting is (obviously?) a lot faster than running several functions that check some constraints.

For SOL_SAFE_USERTYPE specifically, if you search it in the codebase you can see for example this part which introduces a stack check which is overhead compared to not doing it. Overall seems like most changes related to the setting are similar. Just a check-get instead of plain get, followed by code that does a few IF checks on the value to determine if it is nil.

Since I'm writing a gameserver, for us performance is critical. I guess I'll have to dig deeper. It's weird that suddenly this issue came up and maybe there's a fix for it that doesn't require changing safeties or introducing overhead.

McKillroy commented 1 year ago

So - the error lies here: https://github.com/ThePhD/sol2/blob/eba86625b707e3c8c99bbfc4624e51f42dc9e561/include/sol/usertype_container.hpp#L527-L543 The upper code branch compiles on debug and on release, while the lower branch for my code leads to an error in release mode. I have no idea why, or what to do to fix it.

/// This first part works
auto eventtype_test_table = solstate_.new_usertype<TestMessage>(
        "TestEvent",
        sol::factories( &MessageFactory<TestMessage> )
);
/// This part breaks with the error message 
eventtype_test_table[ "arg" ] = &TestMessage::args;

The error:

usertype_container.hpp(541,12): error : non-const lvalue reference to type 'basic_string<...>' cannot bind to a temporary of type 'basic_string<...>'
                                  return stack::unqualified_get<T>(L_, 1);
                                         ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

For some reason it has an issue with "arg" in release mode if no safeties are enabled.

McKillroy commented 1 year ago

Just for completeness - wondering if it is the member I am trying provide as "arg":

std::vector<vardata> args { };

and

using vardata = std::variant< //
    /* CAVEAT!
     * int64_t MUST come before double, or Lua assignments
     * may do unwanted conversions from int to double !!!!
     * */
    int64_t,                      // MUST be first
    double,                       // MUST be AFTER int64_t !!!!!
    std::shared_ptr<std::string>, // 
    hpx::id_type /* LAST */       // Could be anywhere, but better last
    >;

I just realized that removing the shared_ptr made that code compile and the same problem coming up at another location where I tried to expose some std::shared_ptr.

This attempt also failed:

auto shared_string_table = //
        solstate_.new_usertype<std::shared_ptr<std::string>>( "SharedString", restricted_enrollments );
    shared_string_table[ "new" ]        = &std::make_shared<std::string>;

    shared_string_table[ "get" ] = []( std::shared_ptr<std::string> p ) -> std::string //
    {                                                                                  //
        return static_cast<std::string>( *p );
    };

So - could I expose shared_ptr or is there an issue?

McKillroy commented 1 year ago

So after removing the shared_ptr from the variant and removing the shared_string_table, now the compiles work without safeties again. But I don't really understand it - I'd love to have that functionality but don't know how to do it now. I still don't really understand the problem.

McKillroy commented 1 year ago

I tried something more intuitively than knowing what I was doing. I changed this line of code: https://github.com/ThePhD/sol2/blob/eba86625b707e3c8c99bbfc4624e51f42dc9e561/include/sol/usertype_container.hpp#L541 into this:

return *stack::unqualified_get<T*>(L_, 1); 

And my sorrows went away.

Please someone explain if this is OK and could be used as a fix or is just utter hack and will make things explode in the near future.

McKillroy commented 1 year ago

I resorted to asking ChatGPT and that's the answer I got. Is this correct or nonsensical? It kinda makes sense to me. Can someone chime in who really understands what's happening?

ChatGPT answer:


I see what you did there! By changing the return statement to return stack::unqualified_get<T>(L_, 1);, you're dereferencing the pointer returned by stack::unqualifiedget<T*>(L, 1) and returning a reference to the object pointed to by the pointer.

Here's why this works:

When you pass a usertype to a Lua function using Sol2, Sol2 stores a pointer to the object in the Lua registry. When the Lua function is called, Sol2 retrieves this pointer and passes it to the C++ function. By default, Sol2 uses stack::unqualified_get to retrieve the pointer from the Lua stack.

However, when Sol2 safeties are turned off, stack::unqualified_get returns a raw pointer to the object in the Lua registry. This means that if you have a usertype that uses a smart pointer to manage its lifetime, Sol2 won't be able to tell when the object has been deleted.

By changing the return statement to return stack::unqualified_get<T>(L_, 1);, you're dereferencing the raw pointer returned by stack::unqualifiedget<T*>(L, 1) and returning a reference to the object pointed to by the pointer. This means that Sol2 can properly manage the lifetime of the object using the smart pointer.

Note that this approach only works if your usertype is designed to work with raw pointers. If your usertype is designed to work with smart pointers, you should consider using std::shared_ptr or std::unique_ptr to manage the lifetime of your objects.

I hope this helps! Let me know if you have any more questions.


McKillroy commented 1 year ago

I finally worked around the issue by replacing the variant type stored in a vector with a variant wrapper with dedicated getters and constructors so Lua can understand it.