From d1c80a30ee8b13c7331a3e410b4d4f5e05c0dd21 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Sat, 13 Sep 2025 16:31:03 +0530 Subject: [PATCH 01/58] introducing rtl::detail::lambda_table --- ReflectionTemplateLib/access/inc/Function.h | 2 + ReflectionTemplateLib/access/inc/Function.hpp | 12 ++ .../detail/inc/CallReflector.h | 9 +- .../detail/inc/FunctionCaller.hpp | 10 +- .../detail/inc/FunctorContainer.h | 40 +++-- ReflectionTemplateLib/detail/inc/FunctorId.h | 103 +++++------ .../detail/inc/LambdaTable.h | 82 +++++++++ .../detail/inc/MethodContainer.h | 54 ++++-- .../detail/inc/SetupConstructor.hpp | 18 +- .../detail/inc/SetupFunction.hpp | 14 +- .../detail/inc/SetupMethod.hpp | 166 +++++++++--------- .../detail/src/CMakeLists.txt | 1 + 12 files changed, 332 insertions(+), 179 deletions(-) create mode 100644 ReflectionTemplateLib/detail/inc/LambdaTable.h diff --git a/ReflectionTemplateLib/access/inc/Function.h b/ReflectionTemplateLib/access/inc/Function.h index 42d0bd4a..88192f05 100644 --- a/ReflectionTemplateLib/access/inc/Function.h +++ b/ReflectionTemplateLib/access/inc/Function.h @@ -67,6 +67,8 @@ namespace rtl { const std::size_t hasSignatureId(const std::size_t pSignatureId) const; + const detail::FunctorId* hasFunctorId(const std::size_t pSignatureId) const; + GETTER(detail::methodQ, Qualifier, m_qualifier); GETTER_REF(std::vector, FunctorIds, m_functorIds) diff --git a/ReflectionTemplateLib/access/inc/Function.hpp b/ReflectionTemplateLib/access/inc/Function.hpp index 4c620c71..b00ddf0d 100644 --- a/ReflectionTemplateLib/access/inc/Function.hpp +++ b/ReflectionTemplateLib/access/inc/Function.hpp @@ -63,4 +63,16 @@ namespace rtl } return rtl::index_none; } + + + FORCE_INLINE const detail::FunctorId* Function::hasFunctorId(const std::size_t pSignatureId) const + { + //simple linear-search, efficient for small set of elements. + for (const auto& functorId : m_functorIds) { + if (functorId.getSignatureId() == pSignatureId) [[likely]] { + return &functorId; + } + } + return nullptr; + } } diff --git a/ReflectionTemplateLib/detail/inc/CallReflector.h b/ReflectionTemplateLib/detail/inc/CallReflector.h index fad4ecd6..5b0abb0f 100644 --- a/ReflectionTemplateLib/detail/inc/CallReflector.h +++ b/ReflectionTemplateLib/detail/inc/CallReflector.h @@ -14,6 +14,7 @@ #include #include "RObject.h" #include "Constants.h" +#include "FunctorId.h" namespace rtl::detail { @@ -30,10 +31,14 @@ namespace rtl::detail { * gets the lambda vector from '_derivedType' and calls the lambda at given index with '_args'. * this 'forwardCall' is for calling lambda containing non-member-function and static-member-function functors. */ template - FORCE_INLINE static Return forwardCall(std::size_t pFunctorIndex, _params&&..._args) + FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, _params&&..._args) { + // static_cast to derived type, gaurateed safe by design. + //auto lambdaTable = static_cast<_derivedType::lambda_t*>(pFunctorId.m_lambdaTable); + //return lambdaTable->get()[pFunctorId.m_index](std::forward<_params>(_args)...); + //'getFunctors()' must be implemented by _derivedType (FunctorContainer). - return _derivedType::getFunctors()[pFunctorIndex](std::forward<_params>(_args)...); + return _derivedType::getFunctors()[pFunctorId.m_index](std::forward<_params>(_args)...); } diff --git a/ReflectionTemplateLib/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/detail/inc/FunctionCaller.hpp index a673afd5..de652d62 100644 --- a/ReflectionTemplateLib/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/detail/inc/FunctionCaller.hpp @@ -26,9 +26,13 @@ namespace rtl::detail FunctorContainer...>, FunctorContainer<_signature...>>; - std::size_t index = m_function->hasSignatureId(Container::getContainerId()); - if (index != rtl::index_none) [[likely]] { - return Container::template forwardCall<_args...>(index, std::forward<_args>(params)...); + //auto containerId = Container::getContainerId(); + //const detail::FunctorId* functorId = m_function->hasFunctorId(containerId); + //return { error::None, RObject{} }; + + const detail::FunctorId* functorId = m_function->hasFunctorId(Container::getContainerId()); + if (functorId != nullptr) [[likely]] { + return Container::template forwardCall<_args...>(*functorId, std::forward<_args>(params)...); } return { error::SignatureMismatch, RObject{} }; } diff --git a/ReflectionTemplateLib/detail/inc/FunctorContainer.h b/ReflectionTemplateLib/detail/inc/FunctorContainer.h index 425ad930..8f96bc5a 100644 --- a/ReflectionTemplateLib/detail/inc/FunctorContainer.h +++ b/ReflectionTemplateLib/detail/inc/FunctorContainer.h @@ -15,6 +15,7 @@ #include #include +#include "LambdaTable.h" #include "Constants.h" #include "CallReflector.h" #include "SetupFunction.h" @@ -27,10 +28,10 @@ namespace rtl { //forward decl class ReflectionBuilder; - /* @class: FunctorContainer - @param: '_signature...' (combination of any types) - * container class for holding lambda's wrapping functor, constructor calls of same signatures. - * maintains a std::vector with static lifetime. + /* @class: FunctorContainer + @param: '_signature...' (combination of any types) + * container class for holding lambda's wrapping functor, constructor calls of same signatures. + * maintains a std::vector with static lifetime. */ template class FunctorContainer : public SetupFunction>, public SetupConstructor>, @@ -39,6 +40,8 @@ namespace rtl { using FunctionLambda = std::function < Return(_signature...) >; public: + using lambda_t = detail::functors<_signature...>; + //every FunctorContainer<...> will have a unique-id. FORCE_INLINE static std::size_t getContainerId() { static const std::size_t containerId = generate_unique_id(); @@ -67,26 +70,37 @@ namespace rtl { return functorTable; } + static lambda_t& lambdaCache() + { + static lambda_t functorsCache; + return functorsCache; + } + /* @method: pushBack @params: pFunctor (lambda containing functor or constructor call) - pGetIndex (lambda providing index if the functor is already registered) - pUpdate (lambda updating the already registered functors/ctor/d'tor set) + pGetIndex (lambda providing index if the functor is already registered) + pUpdate (lambda updating the already registered functors/ctor/d'tor set) @return: index of newly added or already existing lambda in vector 'm_functors'. - */ static std::size_t pushBack(const FunctionLambda& pFunctor, - std::function pGetIndex, - std::function pUpdate) + */ static std::pair pushBack(const FunctionLambda& pFunctor, + std::function pGetIndex, + std::function pUpdate) { //critical section, thread safe. static std::mutex mtx; std::lock_guard lock(mtx); std::size_t index = pGetIndex(); - if (index == rtl::index_none) { - index = getFunctorTable().size(); - pUpdate(index); + if (index == rtl::index_none) + { + index = lambdaCache().get().size(); + + lambdaCache().pushBack(pFunctor); + getFunctorTable().push_back(pFunctor); + + pUpdate(index); } - return index; + return { index, &lambdaCache() }; } //friends :) diff --git a/ReflectionTemplateLib/detail/inc/FunctorId.h b/ReflectionTemplateLib/detail/inc/FunctorId.h index 5fee2669..b15d804e 100644 --- a/ReflectionTemplateLib/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/detail/inc/FunctorId.h @@ -14,64 +14,65 @@ #include "TypeId.h" #include "Constants.h" -namespace rtl +namespace rtl::detail { - namespace detail + class lambda_table; + +/* @class: FunctorId + * 'FunctorId' object is generated for every functor (member/non-member function pointer) registered. + * acts as a hash-key to lookup a particular functor in the functor-table. + * first, using 'm_containerId', the functor-table container is found. + * once table is found, the functor is accessed at index 'm_index', (never fails, noexcept) + * 'FunctorId' generated for a each functor is unique, even for overloaded functions. + * multiple registartion of same functor will generate same duplicate 'FunctorId'. +*/ struct FunctorId { - /* @class: FunctorId - * 'FunctorId' object is generated for every functor (member/non-member function pointer) registered. - * acts as a hash-key to lookup a particular functor in the functor-table. - * first, using 'm_containerId', the functor-table container is found. - * once table is found, the functor is accessed at index 'm_index', (never fails, noexcept) - * 'FunctorId' generated for a each functor is unique, even for overloaded functions. - * multiple registartion of same functor will generate same duplicate 'FunctorId'. - */ struct FunctorId - { - //index of the functor in the functor-table. - std::size_t m_index; + //index of the functor in the functor-table. + std::size_t m_index; - //return type-id of the functor registered. - std::size_t m_returnId; + //return type-id of the functor registered. + std::size_t m_returnId; - //if functor is a member-function, type id of class/struct it belongs to. - std::size_t m_recordId; + //if functor is a member-function, type id of class/struct it belongs to. + std::size_t m_recordId; - //containerId of the functor-table. - std::size_t m_containerId; + //containerId of the functor-table. + std::size_t m_containerId; - //signature of functor as string. platform dependent, may not be very much readable format. - std::string m_signature; + //signature of functor as string. platform dependent, may not be very much readable format. + std::string m_signature; - GETTER(std::size_t, Index, m_index) - GETTER(std::size_t, ReturnId, m_returnId); - GETTER(std::size_t, RecordId, m_recordId); - GETTER(std::size_t, SignatureId, m_containerId) - GETTER(std::string, SignatureStr, m_signature) + lambda_table* m_lambdaTable = nullptr; - /* @method: getHashCode() - @return: std::size_t (a unique hash-code for a functor) - * 'm_containerId' will be same for functors(non-member) with same signatures. - * for member functions, a functor will have three atrributes - - signature - - whether it is const or non-const - - class/struct type - 'm_containerId' will be same for functors with same above attributes. - * every functor will have a distinct index in the functor-wrapped-lambda-table. - * so, combination of m_containerId & m_index is unique for every functor. - */ std::size_t getHashCode() const - { - return std::stoull(std::to_string(m_containerId) + - std::to_string(m_index) + - std::to_string(m_recordId) + - std::to_string(m_returnId)); - } + GETTER(std::size_t, Index, m_index) + GETTER(std::size_t, ReturnId, m_returnId); + GETTER(std::size_t, RecordId, m_recordId); + GETTER(std::size_t, SignatureId, m_containerId) + GETTER(std::string, SignatureStr, m_signature) - const bool operator==(const FunctorId& pOther) const - { - return (m_index == pOther.m_index && m_returnId == pOther.m_returnId && - m_recordId == pOther.m_recordId && m_containerId == pOther.m_containerId && - m_signature == pOther.m_signature); - } - }; - } + /* @method: getHashCode() + @return: std::size_t (a unique hash-code for a functor) + * 'm_containerId' will be same for functors(non-member) with same signatures. + * for member functions, a functor will have three atrributes + - signature + - whether it is const or non-const + - class/struct type + 'm_containerId' will be same for functors with same above attributes. + * every functor will have a distinct index in the functor-wrapped-lambda-table. + * so, combination of m_containerId & m_index is unique for every functor. + */ std::size_t getHashCode() const + { + return std::stoull(std::to_string(m_containerId) + + std::to_string(m_index) + + std::to_string(m_recordId) + + std::to_string(m_returnId)); + } + + const bool operator==(const FunctorId& pOther) const + { + return (m_index == pOther.m_index && m_returnId == pOther.m_returnId && + m_recordId == pOther.m_recordId && m_containerId == pOther.m_containerId && + m_signature == pOther.m_signature); + } + }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/LambdaTable.h b/ReflectionTemplateLib/detail/inc/LambdaTable.h new file mode 100644 index 00000000..2d3de000 --- /dev/null +++ b/ReflectionTemplateLib/detail/inc/LambdaTable.h @@ -0,0 +1,82 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include +#include + +#include "Constants.h" + +namespace rtl { + + class RObject; + struct Return; +} + +namespace rtl::detail +{ + class lambda_table { }; +} + + +namespace rtl::detail +{ + template + class functors : public lambda_table + { + using lambda_t = std::function ; + + std::vector m_lambdaTable; + + public: + + GETTER_CREF(std::vector, , m_lambdaTable) + + void pushBack(const lambda_t& pLambda) { + m_lambdaTable.push_back(pLambda); + } + }; + + + template + class const_functors : public lambda_table + { + using lambda_t = std::function ; + + std::vector m_lambdaTable; + + public: + + GETTER_CREF(std::vector, , m_lambdaTable) + + void pushBack(const lambda_t& pLambda) { + m_lambdaTable.push_back(pLambda); + } + }; + + + template + class nonconst_functors : public lambda_table + { + using lambda_t = std::function ; + + std::vector m_lambdaTable; + + public: + + GETTER_CREF(std::vector, , m_lambdaTable) + + void pushBack(const lambda_t& pLambda) { + m_lambdaTable.push_back(pLambda); + } + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/MethodContainer.h b/ReflectionTemplateLib/detail/inc/MethodContainer.h index 3a9ec85a..a81d86e1 100644 --- a/ReflectionTemplateLib/detail/inc/MethodContainer.h +++ b/ReflectionTemplateLib/detail/inc/MethodContainer.h @@ -44,6 +44,8 @@ namespace rtl { public: + using lambda_t = detail::nonconst_functors<_signature...>; + //every MethodContainer will have a unique-id. static std::size_t getContainerId() { //holds unique-id @@ -73,26 +75,37 @@ namespace rtl { return functorTable; } + static lambda_t& lambdaCache() + { + static lambda_t functorsCache; + return functorsCache; + } + /* @method: pushBack @params: pFunctor (lambda containing non-const-member-function functor call) pGetIndex (lambda providing index if the functor is already registered) pUpdate (lambda updating the already registered functors set) @return: index of newly added or already existing lambda in vector 'm_methodPtrs'. - */ static std::size_t pushBack(const MethodLambda& pFunctor, - std::function pGetIndex, - std::function pUpdateIndex) + */ static std::pair pushBack(const MethodLambda& pFunctor, + std::function pGetIndex, + std::function pUpdateIndex) { //critical section, thread safe. static std::mutex mtx; std::lock_guard lock(mtx); std::size_t index = pGetIndex(); - if (index == rtl::index_none) { - index = getFunctorTable().size(); - pUpdateIndex(index); + if (index == rtl::index_none) + { + index = lambdaCache().get().size(); + + lambdaCache().pushBack(pFunctor); + getFunctorTable().push_back(pFunctor); + + pUpdateIndex(index); } - return index; + return { index, &lambdaCache() }; } //friends :) @@ -116,6 +129,8 @@ namespace rtl { public: + using lambda_t = detail::const_functors<_signature...>; + //every MethodContainer will have a unique-id. FORCE_INLINE static std::size_t getContainerId() { //holds unique-id @@ -145,26 +160,37 @@ namespace rtl { return functorTable; } + static lambda_t& lambdaCache() + { + static lambda_t functorsCache; + return functorsCache; + } + /* @method: pushBack @params: pFunctor (lambda containing const-member-function functor call) pGetIndex (lambda providing index if the functor is already registered) pUpdate (lambda updating the already registered functors set) @return: index of newly added or already existing lambda in vector 'm_methodPtrs'. - */ static std::size_t pushBack(const MethodLambda& pFunctor, - std::function pGetIndex, - std::function pUpdateIndex) + */ static std::pair pushBack(const MethodLambda& pFunctor, + std::function pGetIndex, + std::function pUpdateIndex) { //critical section, thread safe. static std::mutex mtx; std::lock_guard lock(mtx); std::size_t index = pGetIndex(); - if (index == rtl::index_none) { - index = getFunctorTable().size(); - pUpdateIndex(index); + if (index == rtl::index_none) + { + index = lambdaCache().get().size(); + + lambdaCache().pushBack(pFunctor); + getFunctorTable().push_back(pFunctor); + + pUpdateIndex(index); } - return index; + return { index, &lambdaCache() }; } //friends :) diff --git a/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp b/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp index e2d025be..8a963920 100644 --- a/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp @@ -133,9 +133,12 @@ namespace rtl::detail }; //add the lambda in 'FunctorContainer'. - std::size_t index = _derivedType::pushBack(getConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); - const auto& signatureStr = _derivedType::template getSignatureStr<_recordType>(true); - return detail::FunctorId(index, recordId, recordId, containerId, signatureStr); + auto [index, lambdaPtr] = _derivedType::pushBack(getConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); + + return detail::FunctorId { + index, recordId, recordId, containerId, + _derivedType::template getSignatureStr<_recordType>(true), lambdaPtr + }; } @@ -162,8 +165,11 @@ namespace rtl::detail }; //add the lambda in 'FunctorContainer'. - std::size_t index = _derivedType::pushBack(getCopyConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); - const auto& signatureStr = _derivedType::template getSignatureStr<_recordType>(true); - return detail::FunctorId(index, recordId, recordId, containerId, signatureStr); + auto [index, lambdaPtr] = _derivedType::pushBack(getCopyConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); + + return detail::FunctorId { + index, recordId, recordId, containerId, + _derivedType::template getSignatureStr<_recordType>(true), lambdaPtr + }; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/SetupFunction.hpp b/ReflectionTemplateLib/detail/inc/SetupFunction.hpp index 07b9931d..916e5193 100644 --- a/ReflectionTemplateLib/detail/inc/SetupFunction.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupFunction.hpp @@ -36,15 +36,15 @@ namespace rtl inline SetupFunction<_derivedType>::FunctionLambda<_signature...> SetupFunction<_derivedType>::getCaller(_returnType(*pFunctor)(_signature...)) { - /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. - this is stored in _derivedType's (FunctorContainer) vector holding lambda's. - */ return [pFunctor](_signature&&...params)-> Return + /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. + this is stored in _derivedType's (FunctorContainer) vector holding lambda's. + */ return [pFunctor](_signature&&...params)-> Return { constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); if constexpr (std::is_reference_v<_returnType>) { /* if the function returns reference, this block will be retained by compiler. - Note: reference to temporary or dangling is not checked here. + Note: reference to temporary or dangling is not checked here. */ using _rawRetType = traits::raw_t<_returnType>; const _rawRetType& retObj = pFunctor(std::forward<_signature>(params)...); return { error::None, @@ -107,12 +107,12 @@ namespace rtl //generate a type-id of '_returnType'. const std::size_t retTypeId = TypeId>::get(); //finally add the lambda 'functor' in 'FunctorContainer' lambda vector and get the index. - const std::size_t index = _derivedType::pushBack(getCaller(pFunctor), getIndex, updateIndex); + auto [index, lambdaPtr] = _derivedType::pushBack(getCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. - return detail::FunctorId{ + return detail::FunctorId { index, retTypeId, pRecordId, _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_returnType>() + _derivedType::template getSignatureStr<_returnType>(), lambdaPtr }; } } diff --git a/ReflectionTemplateLib/detail/inc/SetupMethod.hpp b/ReflectionTemplateLib/detail/inc/SetupMethod.hpp index 78979dae..377361e9 100644 --- a/ReflectionTemplateLib/detail/inc/SetupMethod.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupMethod.hpp @@ -26,9 +26,9 @@ namespace rtl inline SetupMethod<_derivedType>::MethodLambda<_signature...> SetupMethod<_derivedType>::getMethodCaller(void(_recordType::* pFunctor)(_signature...)) { - /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. - this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return + /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. + this is stored in _derivedType's (MethodContainer) vector holding lambda's. + */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return { if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -44,41 +44,41 @@ namespace rtl template template inline SetupMethod<_derivedType>::MethodLambda<_signature...> - SetupMethod<_derivedType>::getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...)) + SetupMethod<_derivedType>::getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...)) { - /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. - this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return - { - if (!pTargetObj.isConstCastSafe()) [[unlikely]] { - return { error::IllegalConstCast, RObject{} }; - } - - constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); - //'target' needs const_cast, since the functor is non-const-member-function. - _recordType& target = const_cast<_recordType&>(pTargetObj.view<_recordType>()->get()); - if constexpr (std::is_reference_v<_returnType>) + /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. + this is stored in _derivedType's (MethodContainer) vector holding lambda's. + */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return { - /* if the function returns reference, this block will be retained by compiler. - Note: reference to temporary or dangling is not checked here. - */ using _rawRetType = traits::raw_t<_returnType>; - const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); - return { error::None, - RObjectBuilder::template - build(&retObj, rtl::index_none, isConstCastSafe) - }; - } - else { + if (!pTargetObj.isConstCastSafe()) [[unlikely]] { + return { error::IllegalConstCast, RObject{} }; + } - auto&& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); - using T = std::remove_cvref_t; + constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); + //'target' needs const_cast, since the functor is non-const-member-function. + _recordType& target = const_cast<_recordType&>(pTargetObj.view<_recordType>()->get()); + if constexpr (std::is_reference_v<_returnType>) + { + /* if the function returns reference, this block will be retained by compiler. + Note: reference to temporary or dangling is not checked here. + */ using _rawRetType = traits::raw_t<_returnType>; + const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + return { error::None, + RObjectBuilder::template + build(&retObj, rtl::index_none, isConstCastSafe) + }; + } + else { - return { error::None, - RObjectBuilder::template - build(std::forward(retObj), rtl::index_none, isConstCastSafe) - }; - } - }; + auto&& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + using T = std::remove_cvref_t; + + return { error::None, + RObjectBuilder::template + build(std::forward(retObj), rtl::index_none, isConstCastSafe) + }; + } + }; } @@ -86,52 +86,52 @@ namespace rtl template template inline SetupMethod<_derivedType>::MethodLambda<_signature...> - SetupMethod<_derivedType>::getMethodCaller(void(_recordType::* pFunctor)(_signature...) const) + SetupMethod<_derivedType>::getMethodCaller(void(_recordType::* pFunctor)(_signature...) const) { - /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. - this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return - { - const _recordType& target = pTargetObj.view<_recordType>()->get(); - (target.*pFunctor)(std::forward<_signature>(params)...); - return { error::None, RObject{} }; - }; + /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. + this is stored in _derivedType's (MethodContainer) vector holding lambda's. + */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return + { + const _recordType& target = pTargetObj.view<_recordType>()->get(); + (target.*pFunctor)(std::forward<_signature>(params)...); + return { error::None, RObject{} }; + }; } template template inline SetupMethod<_derivedType>::MethodLambda<_signature...> - SetupMethod<_derivedType>::getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...) const) + SetupMethod<_derivedType>::getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...) const) { - /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. - this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return - { - constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); - //'target' is const and 'pFunctor' is const-member-function. - const _recordType& target = pTargetObj.view<_recordType>()->get(); - if constexpr (std::is_reference_v<_returnType>) { - /* if the function returns reference, this block will be retained by compiler. - Note: reference to temporary or dangling is not checked here. - */ using _rawRetType = traits::raw_t<_returnType>; - const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); - return { error::None, - RObjectBuilder::template - build(&retObj, rtl::index_none, isConstCastSafe) - }; - } - else { + /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. + this is stored in _derivedType's (MethodContainer) vector holding lambda's. + */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return + { + constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); + //'target' is const and 'pFunctor' is const-member-function. + const _recordType& target = pTargetObj.view<_recordType>()->get(); + if constexpr (std::is_reference_v<_returnType>) { + /* if the function returns reference, this block will be retained by compiler. + Note: reference to temporary or dangling is not checked here. + */ using _rawRetType = traits::raw_t<_returnType>; + const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + return { error::None, + RObjectBuilder::template + build(&retObj, rtl::index_none, isConstCastSafe) + }; + } + else { - auto&& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); - using T = std::remove_cvref_t; + auto&& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + using T = std::remove_cvref_t; - return { error::None, - RObjectBuilder::template - build(std::forward(retObj), rtl::index_none, isConstCastSafe) - }; - } - }; + return { error::None, + RObjectBuilder::template + build(std::forward(retObj), rtl::index_none, isConstCastSafe) + }; + } + }; } @@ -145,9 +145,9 @@ namespace rtl * adds lambda (functor-wrapped) in '_derivedType' (MethodContainer) and maintains functorSet. * thread safe, multiple functors can be registered simultaneously. */ template - template - inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...)) - { + template + inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...)) + { /* set of already registered functors. (static life time). used std::vector, efficient for small sets. std::set/map will be overhead. */ static std::vector> functorSet; @@ -155,7 +155,7 @@ namespace rtl /* adds the generated functor index to the 'functorSet'. (thread safe). called from '_derivedType' (MethodContainer) */ const auto& updateIndex = [&](std::size_t pIndex)->void { - functorSet.emplace_back(pFunctor, pIndex); + functorSet.emplace_back(pFunctor, pIndex); }; /* checks if the 'pFunctor' is already present in 'functorSet'. (thread safe). @@ -179,20 +179,20 @@ namespace rtl if constexpr (std::is_same_v<_returnType, void>) { - const std::size_t index = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. - return detail::FunctorId{ + return detail::FunctorId { index, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>() + _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr }; } else { - const std::size_t index = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. return detail::FunctorId { index, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>() + _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr }; } } @@ -239,20 +239,20 @@ namespace rtl if constexpr (std::is_same_v<_returnType, void>) { - const std::size_t index = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. return detail::FunctorId { index, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>() + _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr }; } else { - const std::size_t index = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. return detail::FunctorId { index, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>() + _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr }; } } diff --git a/ReflectionTemplateLib/detail/src/CMakeLists.txt b/ReflectionTemplateLib/detail/src/CMakeLists.txt index 46ec416a..7db6be7a 100644 --- a/ReflectionTemplateLib/detail/src/CMakeLists.txt +++ b/ReflectionTemplateLib/detail/src/CMakeLists.txt @@ -12,6 +12,7 @@ SET(LOCAL_HEADERS "${PROJECT_SOURCE_DIR}/detail/inc/CxxReflection.h" "${PROJECT_SOURCE_DIR}/detail/inc/FunctionCaller.h" "${PROJECT_SOURCE_DIR}/detail/inc/FunctionCaller.hpp" + "${PROJECT_SOURCE_DIR}/detail/inc/LambdaTable.h" "${PROJECT_SOURCE_DIR}/detail/inc/MethodInvoker.h" "${PROJECT_SOURCE_DIR}/detail/inc/MethodInvoker.hpp" "${PROJECT_SOURCE_DIR}/detail/inc/FunctorContainer.h" From 0af7adf88ac712144e89463e871dd9a574086456 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Sun, 14 Sep 2025 15:20:33 +0530 Subject: [PATCH 02/58] integrated functor/lambda static cache and other types. --- RTLBenchmarkApp/src/ReflectedCall.cpp | 2 +- .../detail/inc/CallReflector.h | 6 +- .../detail/inc/FunctorContainer.h | 29 +- ReflectionTemplateLib/detail/inc/FunctorId.h | 19 +- .../detail/inc/FunctorRegistry.h | 129 ++++++ .../detail/inc/LambdaBridge.h | 35 ++ .../inc/{LambdaTable.h => LambdaRegistry.h} | 42 +- .../detail/inc/MethodContainer.h | 12 +- .../detail/inc/SetupConstructor.hpp | 4 +- .../detail/inc/SetupFunction.h | 12 + .../detail/inc/SetupFunction.hpp | 34 +- .../detail/inc/SetupMethod.h | 92 +++-- .../detail/inc/SetupMethod.hpp | 380 ++++++++---------- .../detail/src/CMakeLists.txt | 4 +- 14 files changed, 485 insertions(+), 315 deletions(-) create mode 100644 ReflectionTemplateLib/detail/inc/FunctorRegistry.h create mode 100644 ReflectionTemplateLib/detail/inc/LambdaBridge.h rename ReflectionTemplateLib/detail/inc/{LambdaTable.h => LambdaRegistry.h} (59%) diff --git a/RTLBenchmarkApp/src/ReflectedCall.cpp b/RTLBenchmarkApp/src/ReflectedCall.cpp index 325c72ea..337c676f 100644 --- a/RTLBenchmarkApp/src/ReflectedCall.cpp +++ b/RTLBenchmarkApp/src/ReflectedCall.cpp @@ -22,7 +22,7 @@ namespace { auto Node = cxx::mirror().getRecord("Node").value(); auto [err, robj] = Node.create(); - if (nodeObj.isEmpty()) { + if (robj.isEmpty()) { std::cout << "[0] nodeObj empty! \n"; } return std::move(robj); diff --git a/ReflectionTemplateLib/detail/inc/CallReflector.h b/ReflectionTemplateLib/detail/inc/CallReflector.h index 5b0abb0f..7a896cfd 100644 --- a/ReflectionTemplateLib/detail/inc/CallReflector.h +++ b/ReflectionTemplateLib/detail/inc/CallReflector.h @@ -33,12 +33,8 @@ namespace rtl::detail { */ template FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, _params&&..._args) { - // static_cast to derived type, gaurateed safe by design. - //auto lambdaTable = static_cast<_derivedType::lambda_t*>(pFunctorId.m_lambdaTable); - //return lambdaTable->get()[pFunctorId.m_index](std::forward<_params>(_args)...); - //'getFunctors()' must be implemented by _derivedType (FunctorContainer). - return _derivedType::getFunctors()[pFunctorId.m_index](std::forward<_params>(_args)...); + return _derivedType::getFunctors()[pFunctorId.m_lambdaIndex](std::forward<_params>(_args)...); } diff --git a/ReflectionTemplateLib/detail/inc/FunctorContainer.h b/ReflectionTemplateLib/detail/inc/FunctorContainer.h index 8f96bc5a..d35e5376 100644 --- a/ReflectionTemplateLib/detail/inc/FunctorContainer.h +++ b/ReflectionTemplateLib/detail/inc/FunctorContainer.h @@ -15,7 +15,7 @@ #include #include -#include "LambdaTable.h" +#include "LambdaRegistry.h" #include "Constants.h" #include "CallReflector.h" #include "SetupFunction.h" @@ -28,10 +28,10 @@ namespace rtl { //forward decl class ReflectionBuilder; - /* @class: FunctorContainer - @param: '_signature...' (combination of any types) - * container class for holding lambda's wrapping functor, constructor calls of same signatures. - * maintains a std::vector with static lifetime. + /* @class: FunctorContainer + @param: '_signature...' (combination of any types) + * container class for holding lambda_hop's wrapping functor, constructor calls of same signatures. + * maintains a std::vector with static lifetime. */ template class FunctorContainer : public SetupFunction>, public SetupConstructor>, @@ -40,7 +40,7 @@ namespace rtl { using FunctionLambda = std::function < Return(_signature...) >; public: - using lambda_t = detail::functors<_signature...>; + using lambda_t = detail::lambda_registry<_signature...>; //every FunctorContainer<...> will have a unique-id. FORCE_INLINE static std::size_t getContainerId() { @@ -62,6 +62,14 @@ namespace rtl { "(" + TypeId<_signature...>::toString() + ")"); } + + static lambda_t& lambdaCache() + { + static lambda_t lambdaRegistry; + return lambdaRegistry; + } + + private: //vector holding lambdas @@ -70,18 +78,13 @@ namespace rtl { return functorTable; } - static lambda_t& lambdaCache() - { - static lambda_t functorsCache; - return functorsCache; - } /* @method: pushBack @params: pFunctor (lambda containing functor or constructor call) pGetIndex (lambda providing index if the functor is already registered) pUpdate (lambda updating the already registered functors/ctor/d'tor set) @return: index of newly added or already existing lambda in vector 'm_functors'. - */ static std::pair pushBack(const FunctionLambda& pFunctor, + */ static std::pair pushBack(const FunctionLambda& pFunctor, std::function pGetIndex, std::function pUpdate) { @@ -94,7 +97,7 @@ namespace rtl { { index = lambdaCache().get().size(); - lambdaCache().pushBack(pFunctor); + lambdaCache().push(pFunctor); getFunctorTable().push_back(pFunctor); diff --git a/ReflectionTemplateLib/detail/inc/FunctorId.h b/ReflectionTemplateLib/detail/inc/FunctorId.h index b15d804e..5f606e0f 100644 --- a/ReflectionTemplateLib/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/detail/inc/FunctorId.h @@ -16,7 +16,7 @@ namespace rtl::detail { - class lambda_table; + class lambda_hop; /* @class: FunctorId * 'FunctorId' object is generated for every functor (member/non-member function pointer) registered. @@ -28,7 +28,9 @@ namespace rtl::detail */ struct FunctorId { //index of the functor in the functor-table. - std::size_t m_index; + std::size_t m_lambdaIndex; + + std::size_t m_functorIndex; //return type-id of the functor registered. std::size_t m_returnId; @@ -42,9 +44,9 @@ namespace rtl::detail //signature of functor as string. platform dependent, may not be very much readable format. std::string m_signature; - lambda_table* m_lambdaTable = nullptr; + lambda_hop* m_lambdas = nullptr; - GETTER(std::size_t, Index, m_index) + GETTER(std::size_t, Index, m_lambdaIndex) GETTER(std::size_t, ReturnId, m_returnId); GETTER(std::size_t, RecordId, m_recordId); GETTER(std::size_t, SignatureId, m_containerId) @@ -63,15 +65,18 @@ namespace rtl::detail */ std::size_t getHashCode() const { return std::stoull(std::to_string(m_containerId) + - std::to_string(m_index) + + std::to_string(m_lambdaIndex) + std::to_string(m_recordId) + std::to_string(m_returnId)); } const bool operator==(const FunctorId& pOther) const { - return (m_index == pOther.m_index && m_returnId == pOther.m_returnId && - m_recordId == pOther.m_recordId && m_containerId == pOther.m_containerId && + return (m_returnId == pOther.m_returnId && + m_recordId == pOther.m_recordId && + m_containerId == pOther.m_containerId && + m_lambdaIndex == pOther.m_lambdaIndex && + m_functorIndex == pOther.m_functorIndex && m_signature == pOther.m_signature); } }; diff --git a/ReflectionTemplateLib/detail/inc/FunctorRegistry.h b/ReflectionTemplateLib/detail/inc/FunctorRegistry.h new file mode 100644 index 00000000..72b62908 --- /dev/null +++ b/ReflectionTemplateLib/detail/inc/FunctorRegistry.h @@ -0,0 +1,129 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +namespace rtl { + struct Return; +} + + +namespace rtl::detail +{ + class functor_hop {}; +} + + +namespace rtl::detail +{ + template + class functor_registry : public functor_hop + { + using functor_t = return_t(*)(signature_ts...); + + std::vector> m_functors; + + public: + + functor_t operator[](std::size_t index) { + return m_functors[index].first; + } + + void push(functor_t fptr, std::size_t lambda_index) { + m_functors.emplace_back(fptr, lambda_index); + } + + std::size_t find(functor_t fptr) + { + //linear search, efficient for small set. + for (const auto& itr : m_functors) { + if (itr.first == fptr) { + //functor already registered, return its 'index'. + return itr.second; + } + } + //functor is not already registered, return '-1'. + return rtl::index_none; + } + }; +} + + +namespace rtl::detail +{ + template + class method_registry : public functor_hop + { + using functor_t = return_t(record_t::*)(signature_ts...); + + std::vector> m_functors; + + public: + + functor_t operator[](std::size_t index) { + return m_functors[index].first; + } + + void push(functor_t fptr, std::size_t lambda_index) { + m_functors.emplace_back(fptr, lambda_index); + } + + std::size_t find(functor_t fptr) + { + //linear search, efficient for small set. + for (const auto& itr : m_functors) { + if (itr.first == fptr) { + //functor already registered, return its 'index'. + return itr.second; + } + } + //functor is not already registered, return '-1'. + return rtl::index_none; + } + }; +} + + +namespace rtl::detail +{ + template + class const_method_registry : public functor_hop + { + using functor_t = return_t(record_t::*)(signature_ts...) const; + + std::vector> m_functors; + + public: + + functor_t operator[](std::size_t index) { + return m_functors[index].first; + } + + void push(functor_t fptr, std::size_t lambda_index) { + m_functors.emplace_back(fptr, lambda_index); + } + + std::size_t find(functor_t fptr) + { + //linear search, efficient for small set. + for (const auto& itr : m_functors) { + if (itr.first == fptr) { + //functor already registered, return its 'index'. + return itr.second; + } + } + //functor is not already registered, return '-1'. + return rtl::index_none; + } + }; +} diff --git a/ReflectionTemplateLib/detail/inc/LambdaBridge.h b/ReflectionTemplateLib/detail/inc/LambdaBridge.h new file mode 100644 index 00000000..9a5387c5 --- /dev/null +++ b/ReflectionTemplateLib/detail/inc/LambdaBridge.h @@ -0,0 +1,35 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "FunctorId.h" +#include "FunctorRegistry.h" + +namespace rtl { + struct Return; +} + +namespace rtl::detail::bridge +{ + template + struct lambda_def + { + template + static auto get() + { + return [](const FunctorId& functorId, signature_ts&&...params) + { + + }; + } + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/LambdaTable.h b/ReflectionTemplateLib/detail/inc/LambdaRegistry.h similarity index 59% rename from ReflectionTemplateLib/detail/inc/LambdaTable.h rename to ReflectionTemplateLib/detail/inc/LambdaRegistry.h index 2d3de000..446d8a3e 100644 --- a/ReflectionTemplateLib/detail/inc/LambdaTable.h +++ b/ReflectionTemplateLib/detail/inc/LambdaRegistry.h @@ -11,10 +11,13 @@ #pragma once +#include "LambdaBridge.h" + #include #include #include "Constants.h" +#include "FunctorRegistry.h" namespace rtl { @@ -22,61 +25,70 @@ namespace rtl { struct Return; } + namespace rtl::detail { - class lambda_table { }; + class lambda_hop { }; } namespace rtl::detail { template - class functors : public lambda_table + class lambda_registry : public lambda_hop { - using lambda_t = std::function ; + using lambda_t = std::function; - std::vector m_lambdaTable; + std::vector m_lambdas; + + std::vector m_functors; public: - GETTER_CREF(std::vector, , m_lambdaTable) + GETTER_CREF(std::vector, , m_lambdas) - void pushBack(const lambda_t& pLambda) { - m_lambdaTable.push_back(pLambda); + void push(const lambda_t& pLambda) { + m_lambdas.push_back(pLambda); + } + + Return operator()(std::size_t index, signature_ts&&...params) + { + return m_lambdas[index](m_functors[index], index, std::forward(params)...); } }; + template - class const_functors : public lambda_table + class const_functors : public lambda_hop { using lambda_t = std::function ; - std::vector m_lambdaTable; + std::vector m_lambdas; public: - GETTER_CREF(std::vector, , m_lambdaTable) + GETTER_CREF(std::vector, , m_lambdas) void pushBack(const lambda_t& pLambda) { - m_lambdaTable.push_back(pLambda); + m_lambdas.push_back(pLambda); } }; template - class nonconst_functors : public lambda_table + class nonconst_functors : public lambda_hop { using lambda_t = std::function ; - std::vector m_lambdaTable; + std::vector m_lambdas; public: - GETTER_CREF(std::vector, , m_lambdaTable) + GETTER_CREF(std::vector, , m_lambdas) void pushBack(const lambda_t& pLambda) { - m_lambdaTable.push_back(pLambda); + m_lambdas.push_back(pLambda); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/MethodContainer.h b/ReflectionTemplateLib/detail/inc/MethodContainer.h index a81d86e1..2be9735e 100644 --- a/ReflectionTemplateLib/detail/inc/MethodContainer.h +++ b/ReflectionTemplateLib/detail/inc/MethodContainer.h @@ -86,9 +86,9 @@ namespace rtl { pGetIndex (lambda providing index if the functor is already registered) pUpdate (lambda updating the already registered functors set) @return: index of newly added or already existing lambda in vector 'm_methodPtrs'. - */ static std::pair pushBack(const MethodLambda& pFunctor, - std::function pGetIndex, - std::function pUpdateIndex) + */ static std::pair pushBack(const MethodLambda& pFunctor, + std::function pGetIndex, + std::function pUpdateIndex) { //critical section, thread safe. static std::mutex mtx; @@ -171,9 +171,9 @@ namespace rtl { pGetIndex (lambda providing index if the functor is already registered) pUpdate (lambda updating the already registered functors set) @return: index of newly added or already existing lambda in vector 'm_methodPtrs'. - */ static std::pair pushBack(const MethodLambda& pFunctor, - std::function pGetIndex, - std::function pUpdateIndex) + */ static std::pair pushBack(const MethodLambda& pFunctor, + std::function pGetIndex, + std::function pUpdateIndex) { //critical section, thread safe. static std::mutex mtx; diff --git a/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp b/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp index 8a963920..4673e9f6 100644 --- a/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp @@ -136,7 +136,7 @@ namespace rtl::detail auto [index, lambdaPtr] = _derivedType::pushBack(getConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); return detail::FunctorId { - index, recordId, recordId, containerId, + index, 0, recordId, recordId, containerId, _derivedType::template getSignatureStr<_recordType>(true), lambdaPtr }; } @@ -168,7 +168,7 @@ namespace rtl::detail auto [index, lambdaPtr] = _derivedType::pushBack(getCopyConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); return detail::FunctorId { - index, recordId, recordId, containerId, + index, 0, recordId, recordId, containerId, _derivedType::template getSignatureStr<_recordType>(true), lambdaPtr }; } diff --git a/ReflectionTemplateLib/detail/inc/SetupFunction.h b/ReflectionTemplateLib/detail/inc/SetupFunction.h index 493aa4a9..cdc3b0c2 100644 --- a/ReflectionTemplateLib/detail/inc/SetupFunction.h +++ b/ReflectionTemplateLib/detail/inc/SetupFunction.h @@ -12,6 +12,7 @@ #pragma once #include "FunctorId.h" +#include "FunctorRegistry.h" namespace rtl { @@ -46,5 +47,16 @@ namespace rtl { template static const detail::FunctorId addFunctor(_returnType(*pFunctor)(_signature...), std::size_t pRecordId); }; + + + struct FunctorCache + { + template + static functor_registry& get() + { + static functor_registry functorRegistry; + return functorRegistry; + } + }; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/SetupFunction.hpp b/ReflectionTemplateLib/detail/inc/SetupFunction.hpp index 916e5193..fb665b31 100644 --- a/ReflectionTemplateLib/detail/inc/SetupFunction.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupFunction.hpp @@ -36,9 +36,9 @@ namespace rtl inline SetupFunction<_derivedType>::FunctionLambda<_signature...> SetupFunction<_derivedType>::getCaller(_returnType(*pFunctor)(_signature...)) { - /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. - this is stored in _derivedType's (FunctorContainer) vector holding lambda's. - */ return [pFunctor](_signature&&...params)-> Return + /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. + this is stored in _derivedType's (FunctorContainer) vector holding lambda's. + */ return [pFunctor](_signature&&...params)-> Return { constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); @@ -78,30 +78,16 @@ namespace rtl template inline const detail::FunctorId SetupFunction<_derivedType>::addFunctor(_returnType(*pFunctor)(_signature...), std::size_t pRecordId) { - /* set of already registered functors. (static life time). - used std::vector, since std::set/map are not designed for function pointers - */ static std::vector> functorSet; - - /* adds the generated functor index to the 'functorSet'. (thread safe). - called from '_derivedType' ('FunctorContainer') - */ const auto& updateIndex = [&](std::size_t pIndex)->void + // called from '_derivedType' ('FunctorContainer') + const auto& updateIndex = [pFunctor](std::size_t pIndex)->void { - functorSet.emplace_back(pFunctor, pIndex); + FunctorCache::get<_returnType, _signature...>().push(pFunctor, pIndex); }; - /* checks if the 'pFunctor' is already present in 'functorSet'. (thread safe). - called from '_derivedType' ('FunctorContainer') - */ const auto& getIndex = [&]()-> std::size_t + // called from '_derivedType' ('FunctorContainer') + const auto& getIndex = [pFunctor]()-> std::size_t { - //linear search, efficient for small set. - for (const auto& fptr : functorSet) { - if (fptr.first == pFunctor) { - //functor already registered, return its 'index'. - return fptr.second; - } - } - //functor is not already registered, return '-1'. - return rtl::index_none; + return FunctorCache::get<_returnType, _signature...>().find(pFunctor); }; //generate a type-id of '_returnType'. @@ -111,7 +97,7 @@ namespace rtl //construct the hash-key 'FunctorId' and return. return detail::FunctorId { - index, retTypeId, pRecordId, _derivedType::getContainerId(), + index, 0, retTypeId, pRecordId, _derivedType::getContainerId(), _derivedType::template getSignatureStr<_returnType>(), lambdaPtr }; } diff --git a/ReflectionTemplateLib/detail/inc/SetupMethod.h b/ReflectionTemplateLib/detail/inc/SetupMethod.h index ee521194..3e39090b 100644 --- a/ReflectionTemplateLib/detail/inc/SetupMethod.h +++ b/ReflectionTemplateLib/detail/inc/SetupMethod.h @@ -12,49 +12,67 @@ #pragma once #include "FunctorId.h" +#include "FunctorRegistry.h" -namespace rtl { - - namespace detail - { - /* @struct: SetupMethod - @param: _derivedType (type which inherits this class) - * creates a lambda to perform call on the registered functor. - * adds it to the functor-container, maintains the already added functor set as well. - * deriving classes is MethodContainer & - MethodContainer, which must implement - - - std::size_t& _derived::getContainerId(); - - std::string _derivedType::getSignatureStr(); - - std::size_t& _derived::pushBack(std::function < RObject (error&, const rtl::RObject&, _signature...) >, - std::function, - std::function); - * sets up only non-static-member-function functors in lambda table. - * called from 'ReflectionBuilder', as _derivedType member. - */ template - class SetupMethod - { - template - using MethodLambda = std::function < Return(const rtl::RObject&, _signature...) >; +namespace rtl::detail { + +/* @struct: SetupMethod + @param: _derivedType (type which inherits this class) + * creates a lambda to perform call on the registered functor. + * adds it to the functor-container, maintains the already added functor set as well. + * deriving classes is MethodContainer & + MethodContainer, which must implement - + - std::size_t& _derived::getContainerId(); + - std::string _derivedType::getSignatureStr(); + - std::size_t& _derived::pushBack(std::function < RObject (error&, const rtl::RObject&, _signature...) >, + std::function, + std::function); + * sets up only non-static-member-function functors in lambda table. + * called from 'ReflectionBuilder', as _derivedType member. +*/ template + class SetupMethod + { + template + using MethodLambda = std::function < Return(const rtl::RObject&, _signature...) >; - template - static MethodLambda<_signature...> getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...)); + template + static MethodLambda<_signature...> getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...)); - template - static MethodLambda<_signature...> getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...) const); + template + static MethodLambda<_signature...> getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...) const); - template - static MethodLambda<_signature...> getMethodCaller(void(_recordType::* pFunctor)(_signature...)); + template + static MethodLambda<_signature...> getMethodCaller(void(_recordType::* pFunctor)(_signature...)); - template - static MethodLambda<_signature...> getMethodCaller(void(_recordType::* pFunctor)(_signature...) const); + template + static MethodLambda<_signature...> getMethodCaller(void(_recordType::* pFunctor)(_signature...) const); - protected: + protected: + + template + static const detail::FunctorId addFunctor(_returnType(_recordType::* pFunctor)(_signature...)); - template - static const detail::FunctorId addFunctor(_returnType(_recordType::* pFunctor)(_signature...)); + template + static const detail::FunctorId addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const); + }; - template - static const detail::FunctorId addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const); - }; - } + struct MethodPtrCache + { + template + static method_registry& get() + { + static method_registry methodRegistry; + return methodRegistry; + } + }; + + struct ConstMethodPtrCache + { + template + static const_method_registry& get() + { + static const_method_registry methodRegistry; + return methodRegistry; + } + }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/SetupMethod.hpp b/ReflectionTemplateLib/detail/inc/SetupMethod.hpp index 377361e9..eb4e953f 100644 --- a/ReflectionTemplateLib/detail/inc/SetupMethod.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupMethod.hpp @@ -16,245 +16,217 @@ #include "SetupMethod.h" #include "RObjectBuilder.hpp" -namespace rtl +namespace rtl::detail { - namespace detail + template + template + inline SetupMethod<_derivedType>::MethodLambda<_signature...> + SetupMethod<_derivedType>::getMethodCaller(void(_recordType::* pFunctor)(_signature...)) { - - template - template - inline SetupMethod<_derivedType>::MethodLambda<_signature...> - SetupMethod<_derivedType>::getMethodCaller(void(_recordType::* pFunctor)(_signature...)) + /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. + this is stored in _derivedType's (MethodContainer) vector holding lambda's. + */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return { - /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. - this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return - { - if (!pTargetObj.isConstCastSafe()) [[unlikely]] { - return { error::IllegalConstCast, RObject{} }; - } + if (!pTargetObj.isConstCastSafe()) [[unlikely]] { + return { error::IllegalConstCast, RObject{} }; + } - _recordType& target = const_cast<_recordType&>(pTargetObj.view<_recordType>()->get()); - (target.*pFunctor)(std::forward<_signature>(params)...); - return { error::None, RObject{} }; - }; - } + _recordType& target = const_cast<_recordType&>(pTargetObj.view<_recordType>()->get()); + (target.*pFunctor)(std::forward<_signature>(params)...); + return { error::None, RObject{} }; + }; + } - template - template - inline SetupMethod<_derivedType>::MethodLambda<_signature...> - SetupMethod<_derivedType>::getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...)) + template + template + inline SetupMethod<_derivedType>::MethodLambda<_signature...> + SetupMethod<_derivedType>::getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...)) + { + /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. + this is stored in _derivedType's (MethodContainer) vector holding lambda's. + */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return { - /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. - this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return - { - if (!pTargetObj.isConstCastSafe()) [[unlikely]] { - return { error::IllegalConstCast, RObject{} }; - } + if (!pTargetObj.isConstCastSafe()) [[unlikely]] { + return { error::IllegalConstCast, RObject{} }; + } - constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); - //'target' needs const_cast, since the functor is non-const-member-function. - _recordType& target = const_cast<_recordType&>(pTargetObj.view<_recordType>()->get()); - if constexpr (std::is_reference_v<_returnType>) - { - /* if the function returns reference, this block will be retained by compiler. - Note: reference to temporary or dangling is not checked here. - */ using _rawRetType = traits::raw_t<_returnType>; - const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); - return { error::None, - RObjectBuilder::template - build(&retObj, rtl::index_none, isConstCastSafe) - }; - } - else { + constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); + //'target' needs const_cast, since the functor is non-const-member-function. + _recordType& target = const_cast<_recordType&>(pTargetObj.view<_recordType>()->get()); + if constexpr (std::is_reference_v<_returnType>) + { + /* if the function returns reference, this block will be retained by compiler. + Note: reference to temporary or dangling is not checked here. + */ using _rawRetType = traits::raw_t<_returnType>; + const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + return { error::None, + RObjectBuilder::template + build(&retObj, rtl::index_none, isConstCastSafe) + }; + } + else { - auto&& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); - using T = std::remove_cvref_t; + auto&& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + using T = std::remove_cvref_t; - return { error::None, - RObjectBuilder::template - build(std::forward(retObj), rtl::index_none, isConstCastSafe) - }; - } + return { error::None, + RObjectBuilder::template + build(std::forward(retObj), rtl::index_none, isConstCastSafe) }; - } - + } + }; + } - template - template - inline SetupMethod<_derivedType>::MethodLambda<_signature...> - SetupMethod<_derivedType>::getMethodCaller(void(_recordType::* pFunctor)(_signature...) const) + template + template + inline SetupMethod<_derivedType>::MethodLambda<_signature...> + SetupMethod<_derivedType>::getMethodCaller(void(_recordType::* pFunctor)(_signature...) const) + { + /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. + this is stored in _derivedType's (MethodContainer) vector holding lambda's. + */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return { - /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. - this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return - { - const _recordType& target = pTargetObj.view<_recordType>()->get(); - (target.*pFunctor)(std::forward<_signature>(params)...); - return { error::None, RObject{} }; - }; - } + const _recordType& target = pTargetObj.view<_recordType>()->get(); + (target.*pFunctor)(std::forward<_signature>(params)...); + return { error::None, RObject{} }; + }; + } - template - template - inline SetupMethod<_derivedType>::MethodLambda<_signature...> - SetupMethod<_derivedType>::getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...) const) + template + template + inline SetupMethod<_derivedType>::MethodLambda<_signature...> + SetupMethod<_derivedType>::getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...) const) + { + /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. + this is stored in _derivedType's (MethodContainer) vector holding lambda's. + */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return { - /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. - this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return - { - constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); - //'target' is const and 'pFunctor' is const-member-function. - const _recordType& target = pTargetObj.view<_recordType>()->get(); - if constexpr (std::is_reference_v<_returnType>) { - /* if the function returns reference, this block will be retained by compiler. - Note: reference to temporary or dangling is not checked here. - */ using _rawRetType = traits::raw_t<_returnType>; - const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); - return { error::None, - RObjectBuilder::template - build(&retObj, rtl::index_none, isConstCastSafe) - }; - } - else { + constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); + //'target' is const and 'pFunctor' is const-member-function. + const _recordType& target = pTargetObj.view<_recordType>()->get(); + if constexpr (std::is_reference_v<_returnType>) { + /* if the function returns reference, this block will be retained by compiler. + Note: reference to temporary or dangling is not checked here. + */ using _rawRetType = traits::raw_t<_returnType>; + const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + return { error::None, + RObjectBuilder::template + build(&retObj, rtl::index_none, isConstCastSafe) + }; + } + else { - auto&& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); - using T = std::remove_cvref_t; + auto&& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + using T = std::remove_cvref_t; - return { error::None, - RObjectBuilder::template - build(std::forward(retObj), rtl::index_none, isConstCastSafe) - }; - } + return { error::None, + RObjectBuilder::template + build(std::forward(retObj), rtl::index_none, isConstCastSafe) }; - } + } + }; + } - /* @method: addFunctor(). - @param: 'pFuntor' (a non-const, non-static-member function pointer). - '_derivedType' : class deriving this class ('MethodContainer'). - '_recordType' : the owner 'class/stuct' type of the functor. - '_returnType' : return type deduced from 'pFunctor'. - '_signature...' : function signature deduced from 'pFunctor'. - @return: 'FunctorId' object, a hash-key to lookup the lambda (functor-wrapped) in the _derivedType's lambda-table. - * adds lambda (functor-wrapped) in '_derivedType' (MethodContainer) and maintains functorSet. - * thread safe, multiple functors can be registered simultaneously. - */ template +/* @method: addFunctor(). + @param: 'pFuntor' (a non-const, non-static-member function pointer). + '_derivedType' : class deriving this class ('MethodContainer'). + '_recordType' : the owner 'class/stuct' type of the functor. + '_returnType' : return type deduced from 'pFunctor'. + '_signature...' : function signature deduced from 'pFunctor'. + @return: 'FunctorId' object, a hash-key to lookup the lambda (functor-wrapped) in the _derivedType's lambda-table. + * adds lambda (functor-wrapped) in '_derivedType' (MethodContainer) and maintains functorSet. + * thread safe, multiple functors can be registered simultaneously. +*/ template template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...)) { - /* set of already registered functors. (static life time). - used std::vector, efficient for small sets. std::set/map will be overhead. - */ static std::vector> functorSet; - - /* adds the generated functor index to the 'functorSet'. (thread safe). - called from '_derivedType' (MethodContainer) - */ const auto& updateIndex = [&](std::size_t pIndex)->void { - functorSet.emplace_back(pFunctor, pIndex); - }; + // called from '_derivedType' (MethodContainer) + const auto& updateIndex = [pFunctor](std::size_t pIndex)->void + { + MethodPtrCache::get<_recordType, _returnType, _signature...>().push(pFunctor, pIndex); + }; - /* checks if the 'pFunctor' is already present in 'functorSet'. (thread safe). - called from '_derivedType' ('FunctorContainer') - */ const auto& getIndex = [&]()->std::size_t - { - //linear search, efficient for small set. - for (const auto& fptr : functorSet) { - if (fptr.first == pFunctor) { - //functor already registered, return its 'index'. - return fptr.second; - } - } - //functor is not already registered, return '-1'. - return index_none; - }; + // called from '_derivedType' (MethodContainer) + const auto& getIndex = [pFunctor]()-> std::size_t + { + return MethodPtrCache::get<_recordType, _returnType, _signature...>().find(pFunctor); + }; - //generate a type-id of '_returnType'. - const std::size_t retTypeId = TypeId>::get(); - //finally add the lambda 'functor' in 'MethodContainer' lambda vector and get the index. + //generate a type-id of '_returnType'. + const std::size_t retTypeId = TypeId>::get(); + //finally add the lambda 'functor' in 'MethodContainer' lambda vector and get the index. - if constexpr (std::is_same_v<_returnType, void>) - { - auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); - //construct the hash-key 'FunctorId' and return. - return detail::FunctorId { - index, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr - }; - } - else - { - auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); - //construct the hash-key 'FunctorId' and return. - return detail::FunctorId { - index, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr - }; - } + if constexpr (std::is_same_v<_returnType, void>) + { + auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + //construct the hash-key 'FunctorId' and return. + return detail::FunctorId { + index, 0, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), + _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr + }; + } + else + { + auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + //construct the hash-key 'FunctorId' and return. + return detail::FunctorId { + index, 0, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), + _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr + }; } + } - /* @method: addFunctor(). - @param: 'pFuntor' (a const, non-static-member function pointer). - '_derivedType' : class deriving this class ('MethodContainer'). - '_recordType' : the owner 'class/stuct' type of the functor. - '_returnType' : return type deduced from 'pFunctor'. - '_signature...' : function signature deduced from 'pFunctor'. - @return: 'FunctorId' object, a hash-key to lookup the lambda (containing functor) in the _derivedType's lambda table. - * adds lambda (containing functor) in '_derivedType' (MethodContainer) and maintains a functorSet. - * thread safe, multiple functors can be registered simultaneously. - */ template - template - inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const) +/* @method: addFunctor(). + @param: 'pFuntor' (a const, non-static-member function pointer). + '_derivedType' : class deriving this class ('MethodContainer'). + '_recordType' : the owner 'class/stuct' type of the functor. + '_returnType' : return type deduced from 'pFunctor'. + '_signature...' : function signature deduced from 'pFunctor'. + @return: 'FunctorId' object, a hash-key to lookup the lambda (containing functor) in the _derivedType's lambda table. + * adds lambda (containing functor) in '_derivedType' (MethodContainer) and maintains a functorSet. + * thread safe, multiple functors can be registered simultaneously. +*/ template + template + inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const) + { + // called from '_derivedType' (MethodContainer) + const auto& updateIndex = [pFunctor](std::size_t pIndex)->void { - /* set of already registered functors. (static life time). - used std::vector, efficient for small sets. std::set/map will be overhead. - */ static std::vector> functorSet; - const auto& updateIndex = [&](std::size_t pIndex)->void { - functorSet.emplace_back(pFunctor, pIndex); - }; + ConstMethodPtrCache::get<_recordType, _returnType, _signature...>().push(pFunctor, pIndex); + }; - /* adds the generated functor index to the 'functorSet'. (thread safe). - called from '_derivedType' (MethodContainer) - */ const auto& getIndex = [&]()->std::size_t - { - //linear search, efficient for small set. - for (const auto& fptr : functorSet) { - if (fptr.first == pFunctor) { - //functor already registered, return its 'index'. - return fptr.second; - } - } - //functor is not already registered, return '-1'. - return index_none; - }; + // called from '_derivedType' (MethodContainer) + const auto& getIndex = [pFunctor]()-> std::size_t + { + return ConstMethodPtrCache::get<_recordType, _returnType, _signature...>().find(pFunctor); + }; - //generate a type-id of '_returnType'. - const std::size_t retTypeId = TypeId>::get(); - //finally add the lambda 'functor' in 'MethodContainer' lambda vector and get the index. + //generate a type-id of '_returnType'. + const std::size_t retTypeId = TypeId>::get(); + //finally add the lambda 'functor' in 'MethodContainer' lambda vector and get the index. - if constexpr (std::is_same_v<_returnType, void>) - { - auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); - //construct the hash-key 'FunctorId' and return. - return detail::FunctorId { - index, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr - }; - } - else - { - auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); - //construct the hash-key 'FunctorId' and return. - return detail::FunctorId { - index, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr - }; - } + if constexpr (std::is_same_v<_returnType, void>) + { + auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + //construct the hash-key 'FunctorId' and return. + return detail::FunctorId { + index, 0, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), + _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr + }; + } + else + { + auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + //construct the hash-key 'FunctorId' and return. + return detail::FunctorId { + index, 0, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), + _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr + }; } } } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/src/CMakeLists.txt b/ReflectionTemplateLib/detail/src/CMakeLists.txt index 7db6be7a..6152a560 100644 --- a/ReflectionTemplateLib/detail/src/CMakeLists.txt +++ b/ReflectionTemplateLib/detail/src/CMakeLists.txt @@ -8,11 +8,13 @@ set(LOCAL_SOURCES SET(LOCAL_HEADERS + "${PROJECT_SOURCE_DIR}/detail/inc/LambdaBridge.h" + "${PROJECT_SOURCE_DIR}/detail/inc/LambdaRegistry.h" + "${PROJECT_SOURCE_DIR}/detail/inc/FunctorRegistry.h" "${PROJECT_SOURCE_DIR}/detail/inc/CallReflector.h" "${PROJECT_SOURCE_DIR}/detail/inc/CxxReflection.h" "${PROJECT_SOURCE_DIR}/detail/inc/FunctionCaller.h" "${PROJECT_SOURCE_DIR}/detail/inc/FunctionCaller.hpp" - "${PROJECT_SOURCE_DIR}/detail/inc/LambdaTable.h" "${PROJECT_SOURCE_DIR}/detail/inc/MethodInvoker.h" "${PROJECT_SOURCE_DIR}/detail/inc/MethodInvoker.hpp" "${PROJECT_SOURCE_DIR}/detail/inc/FunctorContainer.h" From 5762021ef4fb885026a07887b7daf9f73007dad8 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Sun, 14 Sep 2025 20:48:09 +0530 Subject: [PATCH 03/58] functor/lambda index added to type metadata. --- RTLBenchmarkApp/src/ReflectedCall.cpp | 25 ++++-- ReflectionTemplateLib/access/inc/Function.hpp | 2 +- ReflectionTemplateLib/access/inc/Record.h | 2 +- .../access/src/CMakeLists.txt | 1 + .../access/src/CxxMirror.cpp | 2 +- .../access/src/CxxMirrorToJson.cpp | 8 +- ReflectionTemplateLib/builder/CMakeLists.txt | 4 +- ReflectionTemplateLib/common/forward_decls.h | 19 +++++ .../detail/inc/FunctorCache.h | 58 +++++++++++++ .../detail/inc/FunctorContainer.h | 25 ++---- ReflectionTemplateLib/detail/inc/FunctorId.h | 11 +-- .../detail/inc/FunctorRegistry.h | 65 ++++++++------- .../detail/inc/LambdaBridge.h | 10 +-- .../detail/inc/LambdaCache.h | 59 ++++++++++++++ .../detail/inc/LambdaRegistry.h | 54 ++++++++----- .../detail/inc/MethodContainer.h | 30 +++---- .../detail/inc/SetupConstructor.hpp | 24 ++++-- .../detail/inc/SetupFunction.h | 74 +++++++---------- .../detail/inc/SetupFunction.hpp | 27 +++++-- .../detail/inc/SetupMethod.h | 20 ----- .../detail/inc/SetupMethod.hpp | 81 ++++++++++++++----- .../detail/src/CMakeLists.txt | 9 +++ 22 files changed, 404 insertions(+), 206 deletions(-) create mode 100644 ReflectionTemplateLib/common/forward_decls.h create mode 100644 ReflectionTemplateLib/detail/inc/FunctorCache.h create mode 100644 ReflectionTemplateLib/detail/inc/LambdaCache.h diff --git a/RTLBenchmarkApp/src/ReflectedCall.cpp b/RTLBenchmarkApp/src/ReflectedCall.cpp index 337c676f..ce4048d7 100644 --- a/RTLBenchmarkApp/src/ReflectedCall.cpp +++ b/RTLBenchmarkApp/src/ReflectedCall.cpp @@ -12,26 +12,37 @@ namespace cxx namespace { - static rtl::Function GetMessage = cxx::mirror().getFunction("getMessage").value(); - static rtl::Function SendMessage = cxx::mirror().getFunction("sendMessage").value(); + static rtl::Function GetMessage; + static rtl::Function SendMessage; - static rtl::Method NodeGetMessage = cxx::mirror().getRecord("Node")->getMethod("getMessage").value(); - static rtl::Method NodeSendMessage = cxx::mirror().getRecord("Node")->getMethod("sendMessage").value(); + static rtl::Method NodeGetMessage; + static rtl::Method NodeSendMessage; static rtl::RObject nodeObj = []() { + GetMessage = cxx::mirror().getFunction("getMessage").value(); + + SendMessage = cxx::mirror().getFunction("sendMessage").value(); + auto Node = cxx::mirror().getRecord("Node").value(); + + NodeGetMessage = Node.getMethod("getMessage").value(); + + NodeSendMessage = Node.getMethod("sendMessage").value(); + auto [err, robj] = Node.create(); + if (robj.isEmpty()) { - std::cout << "[0] nodeObj empty! \n"; + std::cout << "[0] error: " << rtl::to_string(err) << "\n"; } + return std::move(robj); }(); } - namespace - { +namespace +{ static auto _test0 = []() { auto err = SendMessage(bm::g_longStr).err; diff --git a/ReflectionTemplateLib/access/inc/Function.hpp b/ReflectionTemplateLib/access/inc/Function.hpp index b00ddf0d..b16039de 100644 --- a/ReflectionTemplateLib/access/inc/Function.hpp +++ b/ReflectionTemplateLib/access/inc/Function.hpp @@ -58,7 +58,7 @@ namespace rtl //simple linear-search, efficient for small set of elements. for (const auto& functorId : m_functorIds) { if (functorId.getSignatureId() == pSignatureId) [[likely]] { - return functorId.getIndex(); + return functorId.getLambdaIndex(); } } return rtl::index_none; diff --git a/ReflectionTemplateLib/access/inc/Record.h b/ReflectionTemplateLib/access/inc/Record.h index 6a608de8..357c2eb7 100644 --- a/ReflectionTemplateLib/access/inc/Record.h +++ b/ReflectionTemplateLib/access/inc/Record.h @@ -94,7 +94,7 @@ namespace rtl { { static_assert(_alloc != rtl::alloc::None, "Instance cannot be created with 'rtl::alloc::None' option."); const auto& method = m_methods.at(detail::ctor_name(m_recordName)); - std::size_t copyCtorIndex = method.getFunctorIds()[detail::Index::CopyCtor].getIndex(); + std::size_t copyCtorIndex = method.getFunctorIds()[detail::Index::CopyCtor].getLambdaIndex(); return method.invokeCtor(_alloc, copyCtorIndex, std::forward<_ctorArgs>(params)...); } diff --git a/ReflectionTemplateLib/access/src/CMakeLists.txt b/ReflectionTemplateLib/access/src/CMakeLists.txt index 2615a2f3..c8935285 100644 --- a/ReflectionTemplateLib/access/src/CMakeLists.txt +++ b/ReflectionTemplateLib/access/src/CMakeLists.txt @@ -12,6 +12,7 @@ SET(COMMON_HEADERS "${PROJECT_SOURCE_DIR}/common/Constants.h" "${PROJECT_SOURCE_DIR}/common/rtl_traits.h" "${PROJECT_SOURCE_DIR}/common/error_codes.h" + "${PROJECT_SOURCE_DIR}/common/forward_decls.h" "${PROJECT_SOURCE_DIR}/common/ConversionUtils.h" "${PROJECT_SOURCE_DIR}/common/RTLibInterface.h" ) diff --git a/ReflectionTemplateLib/access/src/CxxMirror.cpp b/ReflectionTemplateLib/access/src/CxxMirror.cpp index b0167bf2..8ec1eb3e 100644 --- a/ReflectionTemplateLib/access/src/CxxMirror.cpp +++ b/ReflectionTemplateLib/access/src/CxxMirror.cpp @@ -32,7 +32,7 @@ namespace rtl { const Record& record = itr->second; Method ctors = record.getMethod(detail::ctor_name(record.getRecordName())).value(); - std::size_t copyCtorIndex = ctors.getFunctors()[detail::Index::CopyCtor].getIndex(); + std::size_t copyCtorIndex = ctors.getFunctors()[detail::Index::CopyCtor].getLambdaIndex(); const_cast(pTarget).m_objectId.m_clonerIndex = copyCtorIndex; return error::None; } diff --git a/ReflectionTemplateLib/access/src/CxxMirrorToJson.cpp b/ReflectionTemplateLib/access/src/CxxMirrorToJson.cpp index cf03c065..0143cd39 100644 --- a/ReflectionTemplateLib/access/src/CxxMirrorToJson.cpp +++ b/ReflectionTemplateLib/access/src/CxxMirrorToJson.cpp @@ -26,7 +26,13 @@ static const std::string toJson(const FunctorId& pFunctorId) { std::stringstream sout; sout << "{\"containerId\": \"" << std::to_string(pFunctorId.getSignatureId()) << "\","; - sout << "\"index\": \"" << std::to_string(pFunctorId.getIndex()) << "\","; + sout << "\"lambdaIndex\": \"" << std::to_string(pFunctorId.getLambdaIndex()) << "\","; + if (pFunctorId.getFunctorIndex() != rtl::index_none) { + sout << "\"functorIndex\": \"" << std::to_string(pFunctorId.getFunctorIndex()) << "\","; + } + else { + sout << "\"functorIndex\": \"-1\","; + } if (pFunctorId.getRecordId() != TypeId<>::None) { sout << "\"recordId\": \"" << std::to_string(pFunctorId.getRecordId()) << "\","; } diff --git a/ReflectionTemplateLib/builder/CMakeLists.txt b/ReflectionTemplateLib/builder/CMakeLists.txt index 0484adc6..379e654e 100644 --- a/ReflectionTemplateLib/builder/CMakeLists.txt +++ b/ReflectionTemplateLib/builder/CMakeLists.txt @@ -1,7 +1,9 @@ # Create a variable containing the source files for your target SET(COMMON_HEADERS - "${PROJECT_SOURCE_DIR}/common/Constants.h" + "${PROJECT_SOURCE_DIR}/common/rtl_traits.h" + "${PROJECT_SOURCE_DIR}/common/error_codes.h" + "${PROJECT_SOURCE_DIR}/common/forward_decls.h" ) SET(LOCAL_HEADERS diff --git a/ReflectionTemplateLib/common/forward_decls.h b/ReflectionTemplateLib/common/forward_decls.h new file mode 100644 index 00000000..0666b3f2 --- /dev/null +++ b/ReflectionTemplateLib/common/forward_decls.h @@ -0,0 +1,19 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +namespace rtl { + + struct Return; + + class RObject; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/FunctorCache.h b/ReflectionTemplateLib/detail/inc/FunctorCache.h new file mode 100644 index 00000000..1a89a0cd --- /dev/null +++ b/ReflectionTemplateLib/detail/inc/FunctorCache.h @@ -0,0 +1,58 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "Constants.h" +#include "FunctorRegistry.h" + + +namespace rtl::detail +{ + template + struct functor_cache; +} + +namespace rtl::detail +{ + template<> + struct functor_cache + { + template + static functor_registry& get() + { + static functor_registry functors; + return functors; + } + }; + + template<> + struct functor_cache + { + template + static functor_registry_m& get() + { + static functor_registry_m functors; + return functors; + } + }; + + template<> + struct functor_cache + { + template + static functor_registry_m& get() + { + static functor_registry_m functors; + return functors; + } + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/FunctorContainer.h b/ReflectionTemplateLib/detail/inc/FunctorContainer.h index d35e5376..c3d89fc2 100644 --- a/ReflectionTemplateLib/detail/inc/FunctorContainer.h +++ b/ReflectionTemplateLib/detail/inc/FunctorContainer.h @@ -15,7 +15,7 @@ #include #include -#include "LambdaRegistry.h" +#include "LambdaCache.h" #include "Constants.h" #include "CallReflector.h" #include "SetupFunction.h" @@ -40,8 +40,6 @@ namespace rtl { using FunctionLambda = std::function < Return(_signature...) >; public: - using lambda_t = detail::lambda_registry<_signature...>; - //every FunctorContainer<...> will have a unique-id. FORCE_INLINE static std::size_t getContainerId() { static const std::size_t containerId = generate_unique_id(); @@ -62,14 +60,6 @@ namespace rtl { "(" + TypeId<_signature...>::toString() + ")"); } - - static lambda_t& lambdaCache() - { - static lambda_t lambdaRegistry; - return lambdaRegistry; - } - - private: //vector holding lambdas @@ -85,25 +75,26 @@ namespace rtl { pUpdate (lambda updating the already registered functors/ctor/d'tor set) @return: index of newly added or already existing lambda in vector 'm_functors'. */ static std::pair pushBack(const FunctionLambda& pFunctor, - std::function pGetIndex, - std::function pUpdate) + std::function pGetIndex, + std::function pUpdate) { //critical section, thread safe. static std::mutex mtx; std::lock_guard lock(mtx); + auto& lamdba_store = lambda_cache::get<_signature...>(); std::size_t index = pGetIndex(); + if (index == rtl::index_none) { - index = lambdaCache().get().size(); - - lambdaCache().push(pFunctor); + index = lamdba_store.get().size(); + lamdba_store.push(pFunctor); getFunctorTable().push_back(pFunctor); pUpdate(index); } - return { index, &lambdaCache() }; + return { index, &lamdba_store }; } //friends :) diff --git a/ReflectionTemplateLib/detail/inc/FunctorId.h b/ReflectionTemplateLib/detail/inc/FunctorId.h index 5f606e0f..de0f7a89 100644 --- a/ReflectionTemplateLib/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/detail/inc/FunctorId.h @@ -44,9 +44,10 @@ namespace rtl::detail //signature of functor as string. platform dependent, may not be very much readable format. std::string m_signature; - lambda_hop* m_lambdas = nullptr; + lambda_hop* m_lambda = nullptr; - GETTER(std::size_t, Index, m_lambdaIndex) + GETTER(std::size_t, LambdaIndex, m_lambdaIndex) + GETTER(std::size_t, FunctorIndex, m_functorIndex) GETTER(std::size_t, ReturnId, m_returnId); GETTER(std::size_t, RecordId, m_recordId); GETTER(std::size_t, SignatureId, m_containerId) @@ -65,9 +66,9 @@ namespace rtl::detail */ std::size_t getHashCode() const { return std::stoull(std::to_string(m_containerId) + - std::to_string(m_lambdaIndex) + - std::to_string(m_recordId) + - std::to_string(m_returnId)); + std::to_string(m_lambdaIndex) + + std::to_string(m_recordId) + + std::to_string(m_returnId)); } const bool operator==(const FunctorId& pOther) const diff --git a/ReflectionTemplateLib/detail/inc/FunctorRegistry.h b/ReflectionTemplateLib/detail/inc/FunctorRegistry.h index 72b62908..8ef91ea8 100644 --- a/ReflectionTemplateLib/detail/inc/FunctorRegistry.h +++ b/ReflectionTemplateLib/detail/inc/FunctorRegistry.h @@ -13,9 +13,8 @@ #include -namespace rtl { - struct Return; -} +#include "Constants.h" +#include "forward_decls.h" namespace rtl::detail @@ -27,7 +26,7 @@ namespace rtl::detail namespace rtl::detail { template - class functor_registry : public functor_hop + class functor_registry: public functor_hop { using functor_t = return_t(*)(signature_ts...); @@ -35,6 +34,10 @@ namespace rtl::detail public: + const std::vector>& get() { + return m_functors; + } + functor_t operator[](std::size_t index) { return m_functors[index].first; } @@ -43,17 +46,15 @@ namespace rtl::detail m_functors.emplace_back(fptr, lambda_index); } - std::size_t find(functor_t fptr) + std::pair find(functor_t fptr) { //linear search, efficient for small set. - for (const auto& itr : m_functors) { - if (itr.first == fptr) { - //functor already registered, return its 'index'. - return itr.second; + for (int index = 0; index < m_functors.size(); index++) { + if (m_functors[index].first == fptr) { + return { index, m_functors[index].second }; } } - //functor is not already registered, return '-1'. - return rtl::index_none; + return { rtl::index_none, rtl::index_none }; } }; } @@ -61,8 +62,11 @@ namespace rtl::detail namespace rtl::detail { + template + class functor_registry_m; + template - class method_registry : public functor_hop + class functor_registry_m : public functor_hop { using functor_t = return_t(record_t::*)(signature_ts...); @@ -70,6 +74,11 @@ namespace rtl::detail public: + const std::vector>& get() { + return m_functors; + } + + functor_t operator[](std::size_t index) { return m_functors[index].first; } @@ -78,17 +87,15 @@ namespace rtl::detail m_functors.emplace_back(fptr, lambda_index); } - std::size_t find(functor_t fptr) + std::pair find(functor_t fptr) { //linear search, efficient for small set. - for (const auto& itr : m_functors) { - if (itr.first == fptr) { - //functor already registered, return its 'index'. - return itr.second; + for (int index = 0; index < m_functors.size(); index++) { + if (m_functors[index].first == fptr) { + return { index, m_functors[index].second }; } } - //functor is not already registered, return '-1'. - return rtl::index_none; + return { rtl::index_none, rtl::index_none }; } }; } @@ -97,7 +104,7 @@ namespace rtl::detail namespace rtl::detail { template - class const_method_registry : public functor_hop + class functor_registry_m : public functor_hop { using functor_t = return_t(record_t::*)(signature_ts...) const; @@ -105,6 +112,10 @@ namespace rtl::detail public: + const std::vector>& get() { + return m_functors; + } + functor_t operator[](std::size_t index) { return m_functors[index].first; } @@ -113,17 +124,15 @@ namespace rtl::detail m_functors.emplace_back(fptr, lambda_index); } - std::size_t find(functor_t fptr) + std::pair find(functor_t fptr) { //linear search, efficient for small set. - for (const auto& itr : m_functors) { - if (itr.first == fptr) { - //functor already registered, return its 'index'. - return itr.second; + for (int index = 0; index < m_functors.size(); index++) { + if (m_functors[index].first == fptr) { + return { index, m_functors[index].second }; } } - //functor is not already registered, return '-1'. - return rtl::index_none; + return { rtl::index_none, rtl::index_none }; } }; -} +} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/LambdaBridge.h b/ReflectionTemplateLib/detail/inc/LambdaBridge.h index 9a5387c5..b467bf49 100644 --- a/ReflectionTemplateLib/detail/inc/LambdaBridge.h +++ b/ReflectionTemplateLib/detail/inc/LambdaBridge.h @@ -11,13 +11,11 @@ #pragma once +#include "forward_decls.h" + #include "FunctorId.h" #include "FunctorRegistry.h" -namespace rtl { - struct Return; -} - namespace rtl::detail::bridge { template @@ -26,9 +24,9 @@ namespace rtl::detail::bridge template static auto get() { - return [](const FunctorId& functorId, signature_ts&&...params) + return [](const FunctorId& functorId, signature_ts&&...params)-> Return { - + return { error::None, RObject{} }; }; } }; diff --git a/ReflectionTemplateLib/detail/inc/LambdaCache.h b/ReflectionTemplateLib/detail/inc/LambdaCache.h new file mode 100644 index 00000000..8c5daa5c --- /dev/null +++ b/ReflectionTemplateLib/detail/inc/LambdaCache.h @@ -0,0 +1,59 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "LambdaRegistry.h" + + +namespace rtl::detail +{ + template + struct lambda_cache; +} + +namespace rtl::detail +{ + template<> + struct lambda_cache + { + template + static lambda_registry& get() + { + static lambda_registry registry; + return registry; + } + }; + + + template<> + struct lambda_cache + { + template + static lambda_registry& get() + { + static lambda_registry registry; + return registry; + } + }; + + + template<> + struct lambda_cache + { + template + static lambda_registry& get() + { + static lambda_registry registry; + return registry; + } + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/LambdaRegistry.h b/ReflectionTemplateLib/detail/inc/LambdaRegistry.h index 446d8a3e..9bb6aba7 100644 --- a/ReflectionTemplateLib/detail/inc/LambdaRegistry.h +++ b/ReflectionTemplateLib/detail/inc/LambdaRegistry.h @@ -19,12 +19,6 @@ #include "Constants.h" #include "FunctorRegistry.h" -namespace rtl { - - class RObject; - struct Return; -} - namespace rtl::detail { @@ -34,61 +28,77 @@ namespace rtl::detail namespace rtl::detail { + template + class lambda_registry; + template - class lambda_registry : public lambda_hop + class lambda_registry : public lambda_hop { using lambda_t = std::function; - std::vector m_lambdas; + std::vector lambda_table; std::vector m_functors; public: - GETTER_CREF(std::vector, , m_lambdas) + GETTER_CREF(std::vector, , lambda_table) void push(const lambda_t& pLambda) { - m_lambdas.push_back(pLambda); + lambda_table.push_back(pLambda); } Return operator()(std::size_t index, signature_ts&&...params) { - return m_lambdas[index](m_functors[index], index, std::forward(params)...); + return lambda_table[index](m_functors[index], index, std::forward(params)...); } }; - template - class const_functors : public lambda_hop + class lambda_registry : public lambda_hop { using lambda_t = std::function ; - std::vector m_lambdas; + std::vector lambda_table; + + std::vector m_functors; public: - GETTER_CREF(std::vector, , m_lambdas) + GETTER_CREF(std::vector, , lambda_table) - void pushBack(const lambda_t& pLambda) { - m_lambdas.push_back(pLambda); + void push(const lambda_t& pLambda) { + lambda_table.push_back(pLambda); + } + + Return operator()(std::size_t index, signature_ts&&...params) + { + return lambda_table[index](m_functors[index], index, std::forward(params)...); } }; template - class nonconst_functors : public lambda_hop + class lambda_registry : public lambda_hop { using lambda_t = std::function ; - std::vector m_lambdas; + std::vector lambda_table; + + std::vector m_functors; public: - GETTER_CREF(std::vector, , m_lambdas) + GETTER_CREF(std::vector, , lambda_table) - void pushBack(const lambda_t& pLambda) { - m_lambdas.push_back(pLambda); + void push(const lambda_t& pLambda) { + lambda_table.push_back(pLambda); + } + + Return operator()(std::size_t index, signature_ts&&...params) + { + return lambda_table[index](m_functors[index], index, std::forward(params)...); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/MethodContainer.h b/ReflectionTemplateLib/detail/inc/MethodContainer.h index 2be9735e..0763ef7e 100644 --- a/ReflectionTemplateLib/detail/inc/MethodContainer.h +++ b/ReflectionTemplateLib/detail/inc/MethodContainer.h @@ -44,7 +44,7 @@ namespace rtl { public: - using lambda_t = detail::nonconst_functors<_signature...>; + using lambda_t = detail::lambda_registry; //every MethodContainer will have a unique-id. static std::size_t getContainerId() { @@ -75,11 +75,6 @@ namespace rtl { return functorTable; } - static lambda_t& lambdaCache() - { - static lambda_t functorsCache; - return functorsCache; - } /* @method: pushBack @params: pFunctor (lambda containing non-const-member-function functor call) @@ -95,17 +90,19 @@ namespace rtl { std::lock_guard lock(mtx); std::size_t index = pGetIndex(); + auto& lamdba_store = lambda_cache::get<_signature...>(); + if (index == rtl::index_none) { - index = lambdaCache().get().size(); + index = lamdba_store.get().size(); - lambdaCache().pushBack(pFunctor); + lamdba_store.push(pFunctor); getFunctorTable().push_back(pFunctor); pUpdateIndex(index); } - return { index, &lambdaCache() }; + return { index, &lamdba_store }; } //friends :) @@ -129,7 +126,7 @@ namespace rtl { public: - using lambda_t = detail::const_functors<_signature...>; + using lambda_t = detail::lambda_registry; //every MethodContainer will have a unique-id. FORCE_INLINE static std::size_t getContainerId() { @@ -160,11 +157,6 @@ namespace rtl { return functorTable; } - static lambda_t& lambdaCache() - { - static lambda_t functorsCache; - return functorsCache; - } /* @method: pushBack @params: pFunctor (lambda containing const-member-function functor call) @@ -179,18 +171,20 @@ namespace rtl { static std::mutex mtx; std::lock_guard lock(mtx); + auto& lamdba_store = lambda_cache::get<_signature...>(); std::size_t index = pGetIndex(); + if (index == rtl::index_none) { - index = lambdaCache().get().size(); + index = lamdba_store.get().size(); - lambdaCache().pushBack(pFunctor); + lamdba_store.push(pFunctor); getFunctorTable().push_back(pFunctor); pUpdateIndex(index); } - return { index, &lambdaCache() }; + return { index, &lamdba_store }; } //friends :) diff --git a/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp b/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp index 4673e9f6..cc33c5e6 100644 --- a/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp @@ -133,11 +133,17 @@ namespace rtl::detail }; //add the lambda in 'FunctorContainer'. - auto [index, lambdaPtr] = _derivedType::pushBack(getConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); + auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); return detail::FunctorId { - index, 0, recordId, recordId, containerId, - _derivedType::template getSignatureStr<_recordType>(true), lambdaPtr + + lambdaIndex, + rtl::index_none, + recordId, + recordId, + containerId, + _derivedType::template getSignatureStr<_recordType>(true), + lambdaPtr }; } @@ -165,11 +171,17 @@ namespace rtl::detail }; //add the lambda in 'FunctorContainer'. - auto [index, lambdaPtr] = _derivedType::pushBack(getCopyConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); + auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getCopyConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); return detail::FunctorId { - index, 0, recordId, recordId, containerId, - _derivedType::template getSignatureStr<_recordType>(true), lambdaPtr + + lambdaIndex, + rtl::index_none, + recordId, + recordId, + containerId, + _derivedType::template getSignatureStr<_recordType>(true), + lambdaPtr }; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/SetupFunction.h b/ReflectionTemplateLib/detail/inc/SetupFunction.h index cdc3b0c2..894598a6 100644 --- a/ReflectionTemplateLib/detail/inc/SetupFunction.h +++ b/ReflectionTemplateLib/detail/inc/SetupFunction.h @@ -14,49 +14,35 @@ #include "FunctorId.h" #include "FunctorRegistry.h" -namespace rtl { - - namespace detail +namespace rtl::detail +{ +/* @struct: SetupFunction + @param: _derivedType (type which inherits this class) + * creates a functor-wrapped-lambda to perform call on the registered functor. + * adds it to the functor-container, maintains the already added functor set as well. + * deriving classes is FunctorContainer<...>, which must implement - + - std::size_t& _derived::getContainerId(); + - std::string _derivedType::getSignatureStr(); + - std::size_t& _derived::pushBack(std::function, + std::function, + std::function); + * sets up only non-member or static-member-function functors in table. + * called from 'ReflectionBuilder', as _derivedType member. +*/ template + class SetupFunction { - /* @struct: SetupFunction - @param: _derivedType (type which inherits this class) - * creates a functor-wrapped-lambda to perform call on the registered functor. - * adds it to the functor-container, maintains the already added functor set as well. - * deriving classes is FunctorContainer<...>, which must implement - - - std::size_t& _derived::getContainerId(); - - std::string _derivedType::getSignatureStr(); - - std::size_t& _derived::pushBack(std::function, - std::function, - std::function); - * sets up only non-member or static-member-function functors in table. - * called from 'ReflectionBuilder', as _derivedType member. - */ template - class SetupFunction - { - template - using FunctionLambda = std::function < Return(_signature...) >; - - template - static FunctionLambda<_signature...> getCaller(void(*pFunctor)(_signature...)); - - template - static FunctionLambda<_signature...> getCaller(_returnType(*pFunctor)(_signature...)); - - protected: - - template - static const detail::FunctorId addFunctor(_returnType(*pFunctor)(_signature...), std::size_t pRecordId); - }; - - - struct FunctorCache - { - template - static functor_registry& get() - { - static functor_registry functorRegistry; - return functorRegistry; - } - }; - } + template + using FunctionLambda = std::function < Return(_signature...) >; + + template + static FunctionLambda<_signature...> getCaller(void(*pFunctor)(_signature...)); + + template + static FunctionLambda<_signature...> getCaller(_returnType(*pFunctor)(_signature...)); + + protected: + + template + static const detail::FunctorId addFunctor(_returnType(*pFunctor)(_signature...), std::size_t pRecordId); + }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/SetupFunction.hpp b/ReflectionTemplateLib/detail/inc/SetupFunction.hpp index fb665b31..bd6abdda 100644 --- a/ReflectionTemplateLib/detail/inc/SetupFunction.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupFunction.hpp @@ -11,6 +11,7 @@ #pragma once +#include "FunctorCache.h" #include "SetupFunction.h" #include "RObjectBuilder.hpp" @@ -78,27 +79,39 @@ namespace rtl template inline const detail::FunctorId SetupFunction<_derivedType>::addFunctor(_returnType(*pFunctor)(_signature...), std::size_t pRecordId) { + auto& functorCache = functor_cache::get<_returnType, _signature...>(); + std::size_t functorIndex = rtl::index_none; + // called from '_derivedType' ('FunctorContainer') - const auto& updateIndex = [pFunctor](std::size_t pIndex)->void + const auto& updateIndex = [&](std::size_t pIndex)-> void { - FunctorCache::get<_returnType, _signature...>().push(pFunctor, pIndex); + functorIndex = functorCache.get().size(); + functorCache.push(pFunctor, pIndex); }; // called from '_derivedType' ('FunctorContainer') - const auto& getIndex = [pFunctor]()-> std::size_t + const auto& getIndex = [&]()-> std::size_t { - return FunctorCache::get<_returnType, _signature...>().find(pFunctor); + auto [functor_i, lambda_i] = functorCache.find(pFunctor); + functorIndex = functor_i; + return lambda_i; }; //generate a type-id of '_returnType'. const std::size_t retTypeId = TypeId>::get(); //finally add the lambda 'functor' in 'FunctorContainer' lambda vector and get the index. - auto [index, lambdaPtr] = _derivedType::pushBack(getCaller(pFunctor), getIndex, updateIndex); + auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. return detail::FunctorId { - index, 0, retTypeId, pRecordId, _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_returnType>(), lambdaPtr + + lambdaIndex, + functorIndex, + retTypeId, + pRecordId, + _derivedType::getContainerId(), + _derivedType::template getSignatureStr<_returnType>(), + lambdaPtr }; } } diff --git a/ReflectionTemplateLib/detail/inc/SetupMethod.h b/ReflectionTemplateLib/detail/inc/SetupMethod.h index 3e39090b..9219858f 100644 --- a/ReflectionTemplateLib/detail/inc/SetupMethod.h +++ b/ReflectionTemplateLib/detail/inc/SetupMethod.h @@ -55,24 +55,4 @@ namespace rtl::detail { template static const detail::FunctorId addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const); }; - - struct MethodPtrCache - { - template - static method_registry& get() - { - static method_registry methodRegistry; - return methodRegistry; - } - }; - - struct ConstMethodPtrCache - { - template - static const_method_registry& get() - { - static const_method_registry methodRegistry; - return methodRegistry; - } - }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/SetupMethod.hpp b/ReflectionTemplateLib/detail/inc/SetupMethod.hpp index eb4e953f..91faebac 100644 --- a/ReflectionTemplateLib/detail/inc/SetupMethod.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupMethod.hpp @@ -15,6 +15,7 @@ #include "TypeId.h" #include "SetupMethod.h" #include "RObjectBuilder.hpp" +#include "FunctorCache.h" namespace rtl::detail { @@ -144,16 +145,22 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...)) { + auto& functorCache = functor_cache::get<_recordType, _returnType, _signature...>(); + std::size_t functorIndex = rtl::index_none; + // called from '_derivedType' (MethodContainer) - const auto& updateIndex = [pFunctor](std::size_t pIndex)->void + const auto& updateIndex = [&](std::size_t pIndex)->void { - MethodPtrCache::get<_recordType, _returnType, _signature...>().push(pFunctor, pIndex); + functorIndex = functorCache.get().size(); + functorCache.push(pFunctor, pIndex); }; // called from '_derivedType' (MethodContainer) - const auto& getIndex = [pFunctor]()-> std::size_t + const auto& getIndex = [&]()-> std::size_t { - return MethodPtrCache::get<_recordType, _returnType, _signature...>().find(pFunctor); + auto [functor_i, lambda_i] = functorCache.find(pFunctor); + functorIndex = functor_i; + return lambda_i; }; //generate a type-id of '_returnType'. @@ -162,20 +169,32 @@ namespace rtl::detail if constexpr (std::is_same_v<_returnType, void>) { - auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. return detail::FunctorId { - index, 0, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr + + lambdaIndex, + functorIndex, + retTypeId, + TypeId<_recordType>::get(), + _derivedType::getContainerId(), + _derivedType::template getSignatureStr<_recordType, _returnType>(), + lambdaPtr }; } else { - auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. return detail::FunctorId { - index, 0, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr + + lambdaIndex, + functorIndex, + retTypeId, + TypeId<_recordType>::get(), + _derivedType::getContainerId(), + _derivedType::template getSignatureStr<_recordType, _returnType>(), + lambdaPtr }; } } @@ -194,16 +213,23 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const) { + + auto& functorCache = functor_cache::get<_recordType, _returnType, _signature...>(); + std::size_t functorIndex = rtl::index_none; + // called from '_derivedType' (MethodContainer) - const auto& updateIndex = [pFunctor](std::size_t pIndex)->void + const auto& updateIndex = [&](std::size_t pIndex)-> void { - ConstMethodPtrCache::get<_recordType, _returnType, _signature...>().push(pFunctor, pIndex); + functorIndex = functorCache.get().size(); + functorCache.push(pFunctor, pIndex); }; // called from '_derivedType' (MethodContainer) - const auto& getIndex = [pFunctor]()-> std::size_t + const auto& getIndex = [&]()-> std::size_t { - return ConstMethodPtrCache::get<_recordType, _returnType, _signature...>().find(pFunctor); + auto [functor_i, lambda_i] = functorCache.find(pFunctor); + functorIndex = functor_i; + return lambda_i; }; //generate a type-id of '_returnType'. @@ -212,20 +238,33 @@ namespace rtl::detail if constexpr (std::is_same_v<_returnType, void>) { - auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + //construct the hash-key 'FunctorId' and return. return detail::FunctorId { - index, 0, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr + + lambdaIndex, + functorIndex, + retTypeId, + TypeId<_recordType>::get(), + _derivedType::getContainerId(), + _derivedType::template getSignatureStr<_recordType, _returnType>(), + lambdaPtr }; } else { - auto [index, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. - return detail::FunctorId { - index, 0, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), - _derivedType::template getSignatureStr<_recordType, _returnType>(), lambdaPtr + return detail::FunctorId { + + lambdaIndex, + functorIndex, + retTypeId, + TypeId<_recordType>::get(), + _derivedType::getContainerId(), + _derivedType::template getSignatureStr<_recordType, _returnType>(), + lambdaPtr }; } } diff --git a/ReflectionTemplateLib/detail/src/CMakeLists.txt b/ReflectionTemplateLib/detail/src/CMakeLists.txt index 6152a560..d5f37592 100644 --- a/ReflectionTemplateLib/detail/src/CMakeLists.txt +++ b/ReflectionTemplateLib/detail/src/CMakeLists.txt @@ -6,8 +6,17 @@ set(LOCAL_SOURCES ) +SET(COMMON_HEADERS + + "${PROJECT_SOURCE_DIR}/common/rtl_traits.h" + "${PROJECT_SOURCE_DIR}/common/error_codes.h" + "${PROJECT_SOURCE_DIR}/common/forward_decls.h" +) + SET(LOCAL_HEADERS + "${PROJECT_SOURCE_DIR}/detail/inc/LambdaCache.h" + "${PROJECT_SOURCE_DIR}/detail/inc/FunctorCache.h" "${PROJECT_SOURCE_DIR}/detail/inc/LambdaBridge.h" "${PROJECT_SOURCE_DIR}/detail/inc/LambdaRegistry.h" "${PROJECT_SOURCE_DIR}/detail/inc/FunctorRegistry.h" From 98ff22ff332e8646fda038c6a89079bc420a0369 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Mon, 15 Sep 2025 15:00:33 +0530 Subject: [PATCH 04/58] lambda_registry tested with type-identificaton-system --- RTLBenchmarkApp/src/ReflectedCall.cpp | 2 +- .../CxxMirrorTests/CxxMirrorObjectTest.cpp | 10 +- .../RObjectReflecting_stdSharedPtr.cpp | 2 + ReflectionTemplateLib/access/inc/Method.h | 2 +- ReflectionTemplateLib/access/inc/Method.hpp | 10 +- ReflectionTemplateLib/access/inc/RObject.hpp | 12 +- ReflectionTemplateLib/access/inc/Record.h | 4 +- .../access/src/CxxMirror.cpp | 3 +- ReflectionTemplateLib/common/forward_decls.h | 12 +- ReflectionTemplateLib/common/rtl_traits.h | 11 +- .../detail/inc/CallReflector.h | 18 ++- .../detail/inc/FunctionCaller.hpp | 4 - .../detail/inc/FunctorContainer.h | 2 +- .../detail/inc/LambdaRegistry.h | 132 +++++++++++------- .../detail/inc/MethodContainer.h | 4 +- .../detail/inc/MethodInvoker.hpp | 19 +-- .../detail/inc/RObjectBuilder.h | 20 ++- .../detail/inc/RObjectBuilder.hpp | 12 +- ReflectionTemplateLib/detail/inc/RObjectId.h | 26 +++- .../detail/inc/ReflectionBuilder.hpp | 4 +- .../detail/inc/SetupConstructor.h | 12 +- .../detail/inc/SetupConstructor.hpp | 45 ++++-- .../detail/inc/SetupFunction.h | 2 +- .../detail/inc/SetupFunction.hpp | 22 ++- .../detail/inc/SetupMethod.h | 2 +- .../detail/inc/SetupMethod.hpp | 36 +++-- ReflectionTemplateLib/detail/inc/TypeId.h | 49 ++++++- 27 files changed, 301 insertions(+), 176 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCall.cpp b/RTLBenchmarkApp/src/ReflectedCall.cpp index ce4048d7..099d3c44 100644 --- a/RTLBenchmarkApp/src/ReflectedCall.cpp +++ b/RTLBenchmarkApp/src/ReflectedCall.cpp @@ -55,7 +55,7 @@ namespace static auto _test1 = []() { - auto err = NodeSendMessage.bind(nodeObj).call(bm::g_longStr).err; + auto err = NodeSendMessage(nodeObj)(bm::g_longStr).err; if (err != rtl::error::None) { std::cout << "[2] error: " << rtl::to_string(err) << "\n"; diff --git a/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp b/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp index d98723d4..57f445ea 100644 --- a/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp +++ b/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp @@ -116,11 +116,11 @@ namespace rtl_tests // This test demonstrates redundant function registration handling // and argument forwarding quirks for C-style strings. - TEST(CxxMirrorObjectTest, rednudent_registration__std_cstring_function) + TEST(CxxMirrorObjectTest, rednudant_registration__std_cstring_function) { auto cxxMirror = rtl::CxxMirror({ - // Redundent registrations + // Redundant registrations rtl::type().function("strlen").build(std::strlen), rtl::type().function("strlen").build(std::strlen) @@ -185,7 +185,7 @@ namespace rtl_tests } - TEST(CxxMirrorObjectTest, redundent_registration__std_cstring_func_with_global_cstring) + TEST(CxxMirrorObjectTest, redundant_registration__std_cstring_func_with_global_cstring) { auto cxxMirror = rtl::CxxMirror({ @@ -233,7 +233,7 @@ namespace rtl_tests - TEST(CxxMirrorObjectTest, redundent_regis_with_namespace__std_cstring_func_with_global_cstring) + TEST(CxxMirrorObjectTest, redundant_regis_with_namespace__std_cstring_func_with_global_cstring) { auto cxxMirror = rtl::CxxMirror({ // Redundant registrations with different namespaces. @@ -296,7 +296,7 @@ namespace rtl_tests - TEST(CxxMirrorObjectTest, redundent_regis_with_different_names__std_cstring_func_with_global_cstring) + TEST(CxxMirrorObjectTest, redundant_regis_with_different_names__std_cstring_func_with_global_cstring) { auto cxxMirror = rtl::CxxMirror({ // Redundant registrations with different symbolic names. diff --git a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdSharedPtr.cpp b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdSharedPtr.cpp index 30d463fa..5b71d321 100644 --- a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdSharedPtr.cpp +++ b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdSharedPtr.cpp @@ -152,6 +152,7 @@ namespace rtl::unit_test // Copies the underlying value, *not* the wrapper. auto [err, robj0] = robj.clone(); EXPECT_TRUE(err == error::None); + ASSERT_FALSE(robj0.isEmpty()); // Cannot view as shared_ptr, because we cloned the contained value. EXPECT_FALSE(robj0.canViewAs>()); @@ -230,6 +231,7 @@ namespace rtl::unit_test // Copies the underlying value, *not* the wrapper. auto [err, robj0] = robj.clone(); EXPECT_TRUE(err == error::None); + ASSERT_FALSE(robj0.isEmpty()); // Cannot view as shared_ptr, because we cloned the contained value. EXPECT_FALSE(robj0.canViewAs>()); diff --git a/ReflectionTemplateLib/access/inc/Method.h b/ReflectionTemplateLib/access/inc/Method.h index a57bcbf5..60d26ca7 100644 --- a/ReflectionTemplateLib/access/inc/Method.h +++ b/ReflectionTemplateLib/access/inc/Method.h @@ -41,7 +41,7 @@ namespace rtl { //invokes the constructor associated with this 'Method' template - Return invokeCtor(alloc pAllocType, std::size_t pClonerIndex, _args&&...params) const; + Return invokeCtor(alloc pAllocType, const detail::FunctorId& pClonerId, _args&&...params) const; public: diff --git a/ReflectionTemplateLib/access/inc/Method.hpp b/ReflectionTemplateLib/access/inc/Method.hpp index eed7f822..dcff5e13 100644 --- a/ReflectionTemplateLib/access/inc/Method.hpp +++ b/ReflectionTemplateLib/access/inc/Method.hpp @@ -34,13 +34,13 @@ namespace rtl @return: RStatus * calls the constructor with given arguments. */ template - inline Return Method::invokeCtor(alloc pAllocType, std::size_t pClonerIndex, _args&& ...params) const + inline Return Method::invokeCtor(alloc pAllocType, const detail::FunctorId& pClonerId, _args&& ...params) const { - using Container = detail::FunctorContainer...>; + using Container = detail::FunctorContainer...>; - std::size_t index = hasSignatureId(Container::getContainerId()); - if (index != rtl::index_none) [[likely]] { - return Container::template forwardCall<_args...>(index, pAllocType, pClonerIndex, std::forward<_args>(params)...); + const detail::FunctorId* functorId = hasFunctorId(Container::getContainerId()); + if (functorId != nullptr) [[likely]] { + return Container::template forwardCall<_args...>(*functorId, pAllocType, pClonerId, std::forward<_args>(params)...); } return { error::SignatureMismatch, RObject{} }; } diff --git a/ReflectionTemplateLib/access/inc/RObject.hpp b/ReflectionTemplateLib/access/inc/RObject.hpp index 792dfcfd..a34886ea 100644 --- a/ReflectionTemplateLib/access/inc/RObject.hpp +++ b/ReflectionTemplateLib/access/inc/RObject.hpp @@ -196,10 +196,10 @@ namespace rtl template<> inline Return RObject::createCopy() const { - std::size_t pClonerIndex = m_objectId.m_clonerIndex; - if (pClonerIndex != rtl::index_none) + if (m_objectId.m_clonerId.has_value()) { - return traits::Cloner::template forwardCall(pClonerIndex, alloc::Heap, pClonerIndex, *this); + const detail::FunctorId& functorId = m_objectId.m_clonerId.value(); + return traits::Cloner::template forwardCall(functorId, *this, alloc::Heap); } return { error::CloningDisabled, RObject{} }; } @@ -208,10 +208,10 @@ namespace rtl template<> inline Return RObject::createCopy() const { - std::size_t pClonerIndex = m_objectId.m_clonerIndex; - if (pClonerIndex != rtl::index_none) + if (m_objectId.m_clonerId.has_value()) { - return traits::Cloner::template forwardCall(pClonerIndex, alloc::Stack, pClonerIndex, *this); + const detail::FunctorId& functorId = m_objectId.m_clonerId.value(); + return traits::Cloner::template forwardCall(functorId, *this, alloc::Stack); } return { error::CloningDisabled, RObject{} }; } diff --git a/ReflectionTemplateLib/access/inc/Record.h b/ReflectionTemplateLib/access/inc/Record.h index 357c2eb7..e081b37c 100644 --- a/ReflectionTemplateLib/access/inc/Record.h +++ b/ReflectionTemplateLib/access/inc/Record.h @@ -94,8 +94,8 @@ namespace rtl { { static_assert(_alloc != rtl::alloc::None, "Instance cannot be created with 'rtl::alloc::None' option."); const auto& method = m_methods.at(detail::ctor_name(m_recordName)); - std::size_t copyCtorIndex = method.getFunctorIds()[detail::Index::CopyCtor].getLambdaIndex(); - return method.invokeCtor(_alloc, copyCtorIndex, std::forward<_ctorArgs>(params)...); + const detail::FunctorId& clonerId = method.getFunctorIds()[detail::Index::CopyCtor]; + return method.invokeCtor(_alloc, clonerId, std::forward<_ctorArgs>(params)...); } //only class which can create objects of this class & manipulates 'm_methods'. diff --git a/ReflectionTemplateLib/access/src/CxxMirror.cpp b/ReflectionTemplateLib/access/src/CxxMirror.cpp index 8ec1eb3e..9054699d 100644 --- a/ReflectionTemplateLib/access/src/CxxMirror.cpp +++ b/ReflectionTemplateLib/access/src/CxxMirror.cpp @@ -32,8 +32,7 @@ namespace rtl { const Record& record = itr->second; Method ctors = record.getMethod(detail::ctor_name(record.getRecordName())).value(); - std::size_t copyCtorIndex = ctors.getFunctors()[detail::Index::CopyCtor].getLambdaIndex(); - const_cast(pTarget).m_objectId.m_clonerIndex = copyCtorIndex; + const_cast(pTarget).m_objectId.m_clonerId = ctors.getFunctors()[detail::Index::CopyCtor]; return error::None; } return error::CloningDisabled; diff --git a/ReflectionTemplateLib/common/forward_decls.h b/ReflectionTemplateLib/common/forward_decls.h index 0666b3f2..cf60c39a 100644 --- a/ReflectionTemplateLib/common/forward_decls.h +++ b/ReflectionTemplateLib/common/forward_decls.h @@ -11,9 +11,17 @@ #pragma once -namespace rtl { - +namespace rtl +{ struct Return; class RObject; + + namespace detail + { + struct FunctorId; + + template + class FunctorContainer; + } } \ No newline at end of file diff --git a/ReflectionTemplateLib/common/rtl_traits.h b/ReflectionTemplateLib/common/rtl_traits.h index 323c6af3..257ef64a 100644 --- a/ReflectionTemplateLib/common/rtl_traits.h +++ b/ReflectionTemplateLib/common/rtl_traits.h @@ -21,24 +21,17 @@ #include "TypeId.h" #include "Constants.h" +#include "forward_decls.h" namespace rtl { - class RObject; - - namespace detail { - - template - class FunctorContainer; - } - namespace traits { using Converter = std::function< std::any(const std::any&, const detail::EntityKind&, detail::EntityKind&) >; using ConverterPair = std::pair< std::size_t, Converter >; - using Cloner = detail::FunctorContainer; + using Cloner = detail::FunctorContainer; } namespace traits diff --git a/ReflectionTemplateLib/detail/inc/CallReflector.h b/ReflectionTemplateLib/detail/inc/CallReflector.h index 7a896cfd..20ad94a4 100644 --- a/ReflectionTemplateLib/detail/inc/CallReflector.h +++ b/ReflectionTemplateLib/detail/inc/CallReflector.h @@ -34,7 +34,7 @@ namespace rtl::detail { FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, _params&&..._args) { //'getFunctors()' must be implemented by _derivedType (FunctorContainer). - return _derivedType::getFunctors()[pFunctorId.m_lambdaIndex](std::forward<_params>(_args)...); + return _derivedType::getFunctors()[pFunctorId.m_lambdaIndex](pFunctorId, std::forward<_params>(_args)...); } @@ -43,10 +43,18 @@ namespace rtl::detail { * gets the lambda vector from '_derivedType' and calls the lambda at given index with '_args'. * this 'forwardCall' is for calling lambda containing constructors. */ template - FORCE_INLINE static Return forwardCall(std::size_t pFunctorIndex, rtl::alloc pAllocType, std::size_t pClonerIndex, _params&&..._args) + FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, rtl::alloc pAllocType, const detail::FunctorId& pClonerId, _params&&..._args) { //'getFunctors()' must be implemented by _derivedType (FunctorContainer). - return _derivedType::getFunctors()[pFunctorIndex](pAllocType, pClonerIndex, std::forward<_params>(_args)...); + return _derivedType::getFunctors()[pFunctorId.m_lambdaIndex](pFunctorId, pAllocType, pClonerId, std::forward<_params>(_args)...); + } + + + template + FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, const RObject& pSrcObj, rtl::alloc pAllocType) + { + //'getFunctors()' must be implemented by _derivedType (FunctorContainer). + return _derivedType::getFunctors()[pFunctorId.m_lambdaIndex](pFunctorId, pSrcObj, pAllocType); } @@ -55,10 +63,10 @@ namespace rtl::detail { * gets the lambda vector from '_derivedType' and calls the lambda at given index with '_args'. * this 'forwardCall' is for calling lambda containing member-function functors. */ template - FORCE_INLINE static Return forwardCall(const rtl::RObject& pTarget, std::size_t pFunctorIndex, _params&&..._args) + FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, const rtl::RObject& pTarget, _params&&..._args) { //'getMethodFunctors()' is implemented by _derivedType (MethodContainer) - return _derivedType::getMethodFunctors()[pFunctorIndex](pTarget, std::forward<_params>(_args)...); + return _derivedType::getMethodFunctors()[pFunctorId.m_lambdaIndex](pFunctorId, pTarget, std::forward<_params>(_args)...); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/detail/inc/FunctionCaller.hpp index de652d62..f5426d05 100644 --- a/ReflectionTemplateLib/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/detail/inc/FunctionCaller.hpp @@ -26,10 +26,6 @@ namespace rtl::detail FunctorContainer...>, FunctorContainer<_signature...>>; - //auto containerId = Container::getContainerId(); - //const detail::FunctorId* functorId = m_function->hasFunctorId(containerId); - //return { error::None, RObject{} }; - const detail::FunctorId* functorId = m_function->hasFunctorId(Container::getContainerId()); if (functorId != nullptr) [[likely]] { return Container::template forwardCall<_args...>(*functorId, std::forward<_args>(params)...); diff --git a/ReflectionTemplateLib/detail/inc/FunctorContainer.h b/ReflectionTemplateLib/detail/inc/FunctorContainer.h index c3d89fc2..73afd576 100644 --- a/ReflectionTemplateLib/detail/inc/FunctorContainer.h +++ b/ReflectionTemplateLib/detail/inc/FunctorContainer.h @@ -37,7 +37,7 @@ namespace rtl { public SetupConstructor>, public CallReflector> { - using FunctionLambda = std::function < Return(_signature...) >; + using FunctionLambda = std::function < Return(const FunctorId&, _signature...) >; public: //every FunctorContainer<...> will have a unique-id. diff --git a/ReflectionTemplateLib/detail/inc/LambdaRegistry.h b/ReflectionTemplateLib/detail/inc/LambdaRegistry.h index 9bb6aba7..58b15385 100644 --- a/ReflectionTemplateLib/detail/inc/LambdaRegistry.h +++ b/ReflectionTemplateLib/detail/inc/LambdaRegistry.h @@ -13,92 +13,120 @@ #include "LambdaBridge.h" +#include #include #include +#include "TypeId.h" #include "Constants.h" #include "FunctorRegistry.h" namespace rtl::detail { - class lambda_hop { }; + class lambda_hop { + public: + + std::size_t m_signatureId = TypeId<>::None; + std::vector m_argsId; + }; } namespace rtl::detail { - template - class lambda_registry; + template + class lambda_registry; - template - class lambda_registry : public lambda_hop - { - using lambda_t = std::function; + template + class lambda_registry : public lambda_hop + { + using lambda_t = std::function; - std::vector lambda_table; + std::vector lambda_table; - std::vector m_functors; + std::vector m_functors; - public: + public: - GETTER_CREF(std::vector, , lambda_table) + lambda_registry() + { + m_signatureId = TypeId>::get(); + TypeId::get(m_argsId); + } - void push(const lambda_t& pLambda) { - lambda_table.push_back(pLambda); - } + GETTER_CREF(std::vector, , lambda_table) - Return operator()(std::size_t index, signature_ts&&...params) - { - return lambda_table[index](m_functors[index], index, std::forward(params)...); - } - }; + void push(const lambda_t& lambda) + { + lambda_table.push_back(lambda); + } + Return operator()(std::size_t index, signature_ts&&...params) + { + return lambda_table[index](m_functors[index], index, std::forward(params)...); + } + }; - template - class lambda_registry : public lambda_hop - { - using lambda_t = std::function ; - std::vector lambda_table; + template + class lambda_registry : public lambda_hop + { + using lambda_t = std::function ; - std::vector m_functors; + std::vector lambda_table; - public: + std::vector m_functors; - GETTER_CREF(std::vector, , lambda_table) + public: - void push(const lambda_t& pLambda) { - lambda_table.push_back(pLambda); - } + lambda_registry() + { + m_signatureId = TypeId>::get(); + TypeId::get(m_argsId); + } - Return operator()(std::size_t index, signature_ts&&...params) - { - return lambda_table[index](m_functors[index], index, std::forward(params)...); - } - }; + GETTER_CREF(std::vector, , lambda_table) + void push(const lambda_t& lambda) + { + lambda_table.push_back(lambda); + } - template - class lambda_registry : public lambda_hop - { - using lambda_t = std::function ; - - std::vector lambda_table; + Return operator()(std::size_t index, signature_ts&&...params) + { + return lambda_table[index](m_functors[index], index, std::forward(params)...); + } + }; - std::vector m_functors; - public: + template + class lambda_registry : public lambda_hop + { + using lambda_t = std::function ; - GETTER_CREF(std::vector, , lambda_table) + std::vector lambda_table; - void push(const lambda_t& pLambda) { - lambda_table.push_back(pLambda); - } + std::vector m_functors; - Return operator()(std::size_t index, signature_ts&&...params) - { - return lambda_table[index](m_functors[index], index, std::forward(params)...); - } - }; + public: + + lambda_registry() + { + m_signatureId = TypeId>::get(); + TypeId::get(m_argsId); + } + + GETTER_CREF(std::vector, , lambda_table) + + void push(const lambda_t& lambda) + { + lambda_table.push_back(lambda); + } + + Return operator()(std::size_t index, signature_ts&&...params) + { + return lambda_table[index](m_functors[index], index, std::forward(params)...); + } + }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/MethodContainer.h b/ReflectionTemplateLib/detail/inc/MethodContainer.h index 0763ef7e..9d8a53f8 100644 --- a/ReflectionTemplateLib/detail/inc/MethodContainer.h +++ b/ReflectionTemplateLib/detail/inc/MethodContainer.h @@ -40,7 +40,7 @@ namespace rtl { class MethodContainer : public SetupMethod>, public CallReflector> { - using MethodLambda = std::function < Return (const rtl::RObject&, _signature...) >; + using MethodLambda = std::function < Return (const FunctorId&, const rtl::RObject&, _signature...) >; public: @@ -122,7 +122,7 @@ namespace rtl { class MethodContainer : public SetupMethod>, public CallReflector> { - using MethodLambda = std::function < Return (const rtl::RObject&, _signature...) >; + using MethodLambda = std::function < Return (const FunctorId&, const rtl::RObject&, _signature...) >; public: diff --git a/ReflectionTemplateLib/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/detail/inc/MethodInvoker.hpp index fb06f8cd..76a1c4e9 100644 --- a/ReflectionTemplateLib/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/detail/inc/MethodInvoker.hpp @@ -61,23 +61,23 @@ namespace rtl::detail _args&&... params) { using containerConst = detail::MethodContainer; - std::size_t constMethodIndex = pMethod.hasSignatureId(containerConst::getContainerId()); + const FunctorId* constFunctorId = pMethod.hasFunctorId(containerConst::getContainerId()); - if (constMethodIndex != rtl::index_none) [[likely]] + if (constFunctorId != nullptr) [[likely]] { - return containerConst::template forwardCall<_args...>(pTarget, constMethodIndex, std::forward<_args>(params)...); + return containerConst::template forwardCall<_args...>(*constFunctorId, pTarget, std::forward<_args>(params)...); } else [[unlikely]] { using containerNonConst = detail::MethodContainer; - std::size_t nonConstMethodIndex = pMethod.hasSignatureId(containerNonConst::getContainerId()); + const FunctorId* functorId = pMethod.hasFunctorId(containerNonConst::getContainerId()); - if (nonConstMethodIndex != rtl::index_none) + if (functorId != nullptr) { if (!pTarget.isConstCastSafe()) { return { error::ConstOverloadMissing, RObject{} }; } - return containerNonConst::template forwardCall<_args...>(pTarget, nonConstMethodIndex, std::forward<_args>(params)...); + return containerNonConst::template forwardCall<_args...>(*functorId, pTarget, std::forward<_args>(params)...); } } return { error::SignatureMismatch, RObject{} }; @@ -128,9 +128,10 @@ namespace rtl::detail _args&&... params) { using container0 = detail::MethodContainer; - const std::size_t index = pMethod.hasSignatureId(container0::getContainerId()); - if (index != rtl::index_none) [[likely]] { - return container0::template forwardCall<_args...>(pTarget, index, std::forward<_args>(params)...); + const FunctorId* functorId = pMethod.hasFunctorId(container0::getContainerId()); + + if (functorId != nullptr) [[likely]] { + return container0::template forwardCall<_args...>(*functorId, pTarget, std::forward<_args>(params)...); } else { diff --git a/ReflectionTemplateLib/detail/inc/RObjectBuilder.h b/ReflectionTemplateLib/detail/inc/RObjectBuilder.h index b847dacc..58b352b5 100644 --- a/ReflectionTemplateLib/detail/inc/RObjectBuilder.h +++ b/ReflectionTemplateLib/detail/inc/RObjectBuilder.h @@ -11,12 +11,10 @@ #pragma once -#include "rtl_traits.h" +#include -namespace rtl { - class RObject; - struct Return; -} +#include "rtl_traits.h" +#include "forward_decls.h" namespace rtl::detail { @@ -27,10 +25,10 @@ namespace rtl::detail RObjectBuilder(const RObjectBuilder&) = delete; template requires (_allocOn == alloc::Heap) - static RObject build(T&& pVal, std::size_t pClonerIndex, bool pIsConstCastSafe) noexcept; + static RObject build(T&& pVal, std::optional pClonerId, bool pIsConstCastSafe) noexcept; template requires (_allocOn == alloc::Stack) - static RObject build(T&& pVal, std::size_t pClonerIndex, bool pIsConstCastSafe) noexcept; + static RObject build(T&& pVal, std::optional pClonerId, bool pIsConstCastSafe) noexcept; }; } @@ -48,11 +46,11 @@ namespace rtl { if constexpr (std::is_same_v, char>) { return detail::RObjectBuilder::template - build(std::string_view(pArr, N - 1), rtl::index_none, !traits::is_const_v); + build(std::string_view(pArr, N - 1), std::nullopt, !traits::is_const_v); } else { return detail::RObjectBuilder>::template - build(std::vector(pArr, pArr + N), rtl::index_none, !traits::is_const_v); + build(std::vector(pArr, pArr + N), std::nullopt, !traits::is_const_v); } } @@ -64,13 +62,13 @@ namespace rtl if constexpr (traits::std_wrapper<_T>::type == detail::Wrapper::None) { return detail::RObjectBuilder::template - build(std::forward(pVal), rtl::index_none, !traits::is_const_v); + build(std::forward(pVal), std::nullopt, !traits::is_const_v); } else { constexpr bool isConstCastSafe = !traits::is_const_v::value_type>; return detail::RObjectBuilder::template - build(std::forward(pVal), rtl::index_none, isConstCastSafe); + build(std::forward(pVal), std::nullopt, isConstCastSafe); } } } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/RObjectBuilder.hpp b/ReflectionTemplateLib/detail/inc/RObjectBuilder.hpp index 5de6e142..ded14dad 100644 --- a/ReflectionTemplateLib/detail/inc/RObjectBuilder.hpp +++ b/ReflectionTemplateLib/detail/inc/RObjectBuilder.hpp @@ -32,21 +32,21 @@ namespace rtl::detail template template requires (_allocOn == alloc::Heap) - FORCE_INLINE RObject RObjectBuilder::build(T&& pVal, std::size_t pClonerIndex, bool pIsConstCastSafe) noexcept + FORCE_INLINE RObject RObjectBuilder::build(T&& pVal, std::optional pClonerId, bool pIsConstCastSafe) noexcept { using _T = traits::raw_t; return RObject( std::any{ std::in_place_type>, RObjectUPtr<_T>(std::unique_ptr<_T>(static_cast<_T*>(pVal))) }, - RObjectId::create, alloc::Heap>(pClonerIndex, pIsConstCastSafe), + RObjectId::create, alloc::Heap>(pClonerId, pIsConstCastSafe), &getConverters>()); } template template requires (_allocOn == alloc::Stack) - FORCE_INLINE RObject RObjectBuilder::build(T&& pVal, std::size_t pClonerIndex, bool pIsConstCastSafe) noexcept + FORCE_INLINE RObject RObjectBuilder::build(T&& pVal, std::optional pClonerId, bool pIsConstCastSafe) noexcept { using _T = traits::raw_t; constexpr bool isRawPointer = std::is_pointer_v>; @@ -54,7 +54,7 @@ namespace rtl::detail if constexpr (isRawPointer) { return RObject( std::any { static_cast(pVal) }, - RObjectId::create(pClonerIndex, pIsConstCastSafe), + RObjectId::create(pClonerId, pIsConstCastSafe), &getConverters() ); } else @@ -66,7 +66,7 @@ namespace rtl::detail std::in_place_type>, RObjectUPtr(std::move(pVal)) }, - RObjectId::create(pClonerIndex, pIsConstCastSafe), + RObjectId::create(pClonerId, pIsConstCastSafe), &getConverters() ); } else @@ -76,7 +76,7 @@ namespace rtl::detail std::in_place_type, std::forward(pVal) }, - RObjectId::create(pClonerIndex, pIsConstCastSafe), + RObjectId::create(pClonerId, pIsConstCastSafe), &getConverters() ); } } diff --git a/ReflectionTemplateLib/detail/inc/RObjectId.h b/ReflectionTemplateLib/detail/inc/RObjectId.h index 5455ca9f..403e9b96 100644 --- a/ReflectionTemplateLib/detail/inc/RObjectId.h +++ b/ReflectionTemplateLib/detail/inc/RObjectId.h @@ -13,11 +13,11 @@ #include #include -#include "ReflectCast.h" +#include -namespace rtl { - class RObject; -} +#include "ReflectCast.h" +#include "forward_decls.h" +#include "FunctorId.h" namespace rtl::detail { @@ -27,13 +27,14 @@ namespace rtl::detail bool m_isConstCastSafe; std::size_t m_typeId; - std::size_t m_clonerIndex; std::size_t m_wrapperTypeId; alloc m_allocatedOn; Wrapper m_wrapperType; EntityKind m_containsAs; + std::optional m_clonerId; + GETTER(std::size_t, TypeId, m_typeId) GETTER(EntityKind, ContainedAs, m_containsAs) @@ -58,7 +59,7 @@ namespace rtl::detail template - FORCE_INLINE static RObjectId create(std::size_t pClonerIndex, bool pIsConstCastSafe) noexcept + FORCE_INLINE static RObjectId create(std::optional pClonerId, bool pIsConstCastSafe) noexcept { // extract wrapper info. using _W = traits::std_wrapper>; @@ -68,8 +69,19 @@ namespace rtl::detail const std::size_t wrapperId = _W::id(); const std::size_t typeId = rtl::detail::TypeId<_T>::get(); + constexpr bool isWrappingConst = (_W::type != Wrapper::None && traits::is_const_v); - return RObjectId{ isWrappingConst, pIsConstCastSafe, typeId, pClonerIndex, wrapperId, _allocOn, _W::type, entityKind }; + return RObjectId { + + isWrappingConst, + pIsConstCastSafe, + typeId, + wrapperId, + _allocOn, + _W::type, + entityKind, + pClonerId + }; } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/ReflectionBuilder.hpp b/ReflectionTemplateLib/detail/inc/ReflectionBuilder.hpp index 29e96bb4..f6712332 100644 --- a/ReflectionTemplateLib/detail/inc/ReflectionBuilder.hpp +++ b/ReflectionTemplateLib/detail/inc/ReflectionBuilder.hpp @@ -87,9 +87,9 @@ namespace rtl::detail */ template inline const Function ReflectionBuilder::buildConstructor() const { - using Container = FunctorContainer < rtl::alloc, std::size_t, traits::remove_const_if_not_reference<_ctorSignature>... > ; + using Container = FunctorContainer < rtl::alloc, FunctorId, traits::remove_const_if_not_reference<_ctorSignature>... > ; const FunctorId& functorId = Container::template addConstructor<_recordType, _ctorSignature...>(); - const FunctorId& copyCtorId = traits::Cloner::template addCopyConstructor<_recordType, const RObject&>(); + const FunctorId& copyCtorId = traits::Cloner::template addCopyConstructor<_recordType, RObject, alloc>(); const Function& ctorFunction = Function(m_namespace, m_record, m_function, functorId, m_recordId, methodQ::None); ctorFunction.getFunctorIds().push_back(copyCtorId); diff --git a/ReflectionTemplateLib/detail/inc/SetupConstructor.h b/ReflectionTemplateLib/detail/inc/SetupConstructor.h index 44d06345..6dfc38b2 100644 --- a/ReflectionTemplateLib/detail/inc/SetupConstructor.h +++ b/ReflectionTemplateLib/detail/inc/SetupConstructor.h @@ -11,12 +11,12 @@ #pragma once + #include "FunctorId.h" +#include "forward_decls.h" namespace rtl { - class RObject; - namespace detail { /* @struct: SetupConstructor @@ -28,13 +28,15 @@ namespace rtl { class SetupConstructor { template - using CtorLambda = std::function < Return(alloc, std::size_t, _signature...) >; + using CtorLambda = std::function < Return(FunctorId, alloc, FunctorId, _signature...) >; + + using CopyCtorLambda = std::function < Return(const FunctorId&, const RObject&, alloc) >; template static CtorLambda<_signature...> getConstructorCaller(); - template - static CtorLambda<_signature...> getCopyConstructorCaller(); + template + static CopyCtorLambda getCopyConstructorCaller(); protected: diff --git a/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp b/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp index cc33c5e6..e3ca1fb5 100644 --- a/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp @@ -11,6 +11,7 @@ #pragma once #include +#include #include "RObjectBuilder.hpp" #include "SetupConstructor.h" @@ -22,8 +23,11 @@ namespace rtl::detail inline SetupConstructor<_derivedType>::CtorLambda<_signature...> SetupConstructor<_derivedType>::getConstructorCaller() { - return [](alloc pAllocType, std::size_t pClonerIndex, _signature&&...params)-> Return + return [](const FunctorId& pFunctorId, alloc pAllocType, const FunctorId& pClonerId, _signature&&...params)-> Return { + std::size_t signatureId = TypeId...>>::get(); + assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); + if constexpr (sizeof...(_signature) == 0 && !std::is_default_constructible_v<_recordType>) { //default constructor, private or deleted. return { error::TypeNotDefaultConstructible, RObject{} }; @@ -32,24 +36,27 @@ namespace rtl::detail { if (pAllocType == alloc::Stack) { - if constexpr (!std::is_copy_constructible_v<_recordType>) { + if constexpr (!std::is_copy_constructible_v<_recordType>) + { return { error::TypeNotCopyConstructible, RObject{} }; } - else { + else + { return { error::None, RObjectBuilder<_recordType>::template - build(_recordType(std::forward<_signature>(params)...), pClonerIndex, true) + build(_recordType(std::forward<_signature>(params)...), pClonerId, true) }; } } - else if (pAllocType == alloc::Heap) { + else if (pAllocType == alloc::Heap) + { return { error::None, RObjectBuilder<_recordType*>::template - build(new _recordType(std::forward<_signature>(params)...), pClonerIndex, true) + build(new _recordType(std::forward<_signature>(params)...), pClonerId, true) }; } } @@ -60,26 +67,29 @@ namespace rtl::detail template - template - inline SetupConstructor<_derivedType>::CtorLambda<_signature...> + template + inline SetupConstructor<_derivedType>::CopyCtorLambda SetupConstructor<_derivedType>::getCopyConstructorCaller() { if constexpr (std::is_copy_constructible_v<_recordType>) { - return [](alloc pAllocOn, std::size_t pClonerIndex, const RObject& pOther) -> Return + return [](const FunctorId& pFunctorId, const RObject& pOther, alloc pAllocOn) -> Return { + std::size_t signatureId = TypeId>::get(); + assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); + const auto& srcObj = pOther.view<_recordType>()->get(); switch (pAllocOn) { case alloc::Stack: return { error::None, - RObjectBuilder<_recordType>::template build(_recordType(srcObj), pClonerIndex, true) + RObjectBuilder<_recordType>::template build(_recordType(srcObj), pFunctorId, true) }; case alloc::Heap: return { error::None, - RObjectBuilder<_recordType*>::template build(new _recordType(srcObj), pClonerIndex, true) + RObjectBuilder<_recordType*>::template build(new _recordType(srcObj), pFunctorId, true) }; default: return { @@ -91,8 +101,11 @@ namespace rtl::detail } else { - return [](alloc pAllocOn, std::size_t pClonerIndex, const RObject&) -> Return + return [](const FunctorId& pFunctorId, const RObject& pOther, alloc pAllocOn) -> Return { + std::size_t signatureId = TypeId>::get(); + assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); + return { error::TypeNotCopyConstructible, RObject{} @@ -115,6 +128,7 @@ namespace rtl::detail inline const detail::FunctorId SetupConstructor<_derivedType>::addConstructor() { std::size_t recordId = TypeId<_recordType>::get(); + std::size_t returnId = recordId; std::size_t containerId = _derivedType::getContainerId(); std::size_t hashKey = std::stoull(std::to_string(containerId) + std::to_string(recordId)); @@ -139,7 +153,7 @@ namespace rtl::detail lambdaIndex, rtl::index_none, - recordId, + returnId, recordId, containerId, _derivedType::template getSignatureStr<_recordType>(true), @@ -153,6 +167,7 @@ namespace rtl::detail inline const detail::FunctorId SetupConstructor<_derivedType>::addCopyConstructor() { std::size_t recordId = TypeId<_recordType>::get(); + std::size_t returnId = recordId; std::size_t containerId = _derivedType::getContainerId(); std::size_t hashKey = std::stoull(std::to_string(containerId) + std::to_string(recordId)); @@ -171,13 +186,13 @@ namespace rtl::detail }; //add the lambda in 'FunctorContainer'. - auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getCopyConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); + auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getCopyConstructorCaller<_recordType>(), getIndex, updateIndex); return detail::FunctorId { lambdaIndex, rtl::index_none, - recordId, + returnId, recordId, containerId, _derivedType::template getSignatureStr<_recordType>(true), diff --git a/ReflectionTemplateLib/detail/inc/SetupFunction.h b/ReflectionTemplateLib/detail/inc/SetupFunction.h index 894598a6..d8ef3a24 100644 --- a/ReflectionTemplateLib/detail/inc/SetupFunction.h +++ b/ReflectionTemplateLib/detail/inc/SetupFunction.h @@ -32,7 +32,7 @@ namespace rtl::detail class SetupFunction { template - using FunctionLambda = std::function < Return(_signature...) >; + using FunctionLambda = std::function < Return(const FunctorId&, _signature...) >; template static FunctionLambda<_signature...> getCaller(void(*pFunctor)(_signature...)); diff --git a/ReflectionTemplateLib/detail/inc/SetupFunction.hpp b/ReflectionTemplateLib/detail/inc/SetupFunction.hpp index bd6abdda..9390ee3b 100644 --- a/ReflectionTemplateLib/detail/inc/SetupFunction.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupFunction.hpp @@ -11,6 +11,8 @@ #pragma once +#include + #include "FunctorCache.h" #include "SetupFunction.h" #include "RObjectBuilder.hpp" @@ -24,8 +26,11 @@ namespace rtl inline SetupFunction<_derivedType>::FunctionLambda<_signature...> SetupFunction<_derivedType>::getCaller(void(*pFunctor)(_signature...)) { - return [pFunctor](_signature&&... params) -> Return + return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { + std::size_t signatureId = TypeId...>>::get(); + assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); + pFunctor(std::forward<_signature>(params)...); return { error::None, RObject{} }; }; @@ -39,18 +44,21 @@ namespace rtl { /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (FunctorContainer) vector holding lambda's. - */ return [pFunctor](_signature&&...params)-> Return + */ return [pFunctor](const FunctorId& pFunctorId, _signature&&...params)-> Return { constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); + std::size_t signatureId = TypeId...>>::get(); + assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); + if constexpr (std::is_reference_v<_returnType>) { /* if the function returns reference, this block will be retained by compiler. - Note: reference to temporary or dangling is not checked here. + Note: reference to temporary or dangling is not checked here. */ using _rawRetType = traits::raw_t<_returnType>; const _rawRetType& retObj = pFunctor(std::forward<_signature>(params)...); return { error::None, RObjectBuilder::template - build(&retObj, rtl::index_none, isConstCastSafe) + build(&retObj, std::nullopt, isConstCastSafe) }; } else { @@ -60,7 +68,7 @@ namespace rtl return { error::None, RObjectBuilder::template - build(std::forward(retObj), rtl::index_none, isConstCastSafe) + build(std::forward(retObj), std::nullopt, isConstCastSafe) }; } }; @@ -98,7 +106,7 @@ namespace rtl }; //generate a type-id of '_returnType'. - const std::size_t retTypeId = TypeId>::get(); + const std::size_t returnId = TypeId>::get(); //finally add the lambda 'functor' in 'FunctorContainer' lambda vector and get the index. auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getCaller(pFunctor), getIndex, updateIndex); @@ -107,7 +115,7 @@ namespace rtl lambdaIndex, functorIndex, - retTypeId, + returnId, pRecordId, _derivedType::getContainerId(), _derivedType::template getSignatureStr<_returnType>(), diff --git a/ReflectionTemplateLib/detail/inc/SetupMethod.h b/ReflectionTemplateLib/detail/inc/SetupMethod.h index 9219858f..1e08fc9e 100644 --- a/ReflectionTemplateLib/detail/inc/SetupMethod.h +++ b/ReflectionTemplateLib/detail/inc/SetupMethod.h @@ -33,7 +33,7 @@ namespace rtl::detail { class SetupMethod { template - using MethodLambda = std::function < Return(const rtl::RObject&, _signature...) >; + using MethodLambda = std::function < Return(const FunctorId&, const rtl::RObject&, _signature...) >; template static MethodLambda<_signature...> getMethodCaller(_returnType(_recordType::* pFunctor)(_signature...)); diff --git a/ReflectionTemplateLib/detail/inc/SetupMethod.hpp b/ReflectionTemplateLib/detail/inc/SetupMethod.hpp index 91faebac..90f6d9bb 100644 --- a/ReflectionTemplateLib/detail/inc/SetupMethod.hpp +++ b/ReflectionTemplateLib/detail/inc/SetupMethod.hpp @@ -11,6 +11,8 @@ #pragma once +#include + #include "view.h" #include "TypeId.h" #include "SetupMethod.h" @@ -26,8 +28,17 @@ namespace rtl::detail { /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return + */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { + std::size_t signatureId = TypeId...>>::get(); + assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); + + //using lambda_t = lambda_registry...>; + + //lambda_t registry = static_cast(pFunctorId.m_lambda); + + //registry-> + if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; } @@ -46,8 +57,11 @@ namespace rtl::detail { /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return + */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { + std::size_t signatureId = TypeId...>>::get(); + assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); + if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; } @@ -63,7 +77,7 @@ namespace rtl::detail const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); return { error::None, RObjectBuilder::template - build(&retObj, rtl::index_none, isConstCastSafe) + build(&retObj, std::nullopt, isConstCastSafe) }; } else { @@ -73,7 +87,7 @@ namespace rtl::detail return { error::None, RObjectBuilder::template - build(std::forward(retObj), rtl::index_none, isConstCastSafe) + build(std::forward(retObj), std::nullopt, isConstCastSafe) }; } }; @@ -87,8 +101,11 @@ namespace rtl::detail { /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return + */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { + std::size_t signatureId = TypeId...>>::get(); + assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); + const _recordType& target = pTargetObj.view<_recordType>()->get(); (target.*pFunctor)(std::forward<_signature>(params)...); return { error::None, RObject{} }; @@ -103,8 +120,11 @@ namespace rtl::detail { /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const RObject& pTargetObj, _signature&&...params)-> Return + */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { + std::size_t signatureId = TypeId...>>::get(); + assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); + constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); //'target' is const and 'pFunctor' is const-member-function. const _recordType& target = pTargetObj.view<_recordType>()->get(); @@ -115,7 +135,7 @@ namespace rtl::detail const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); return { error::None, RObjectBuilder::template - build(&retObj, rtl::index_none, isConstCastSafe) + build(&retObj, std::nullopt, isConstCastSafe) }; } else { @@ -125,7 +145,7 @@ namespace rtl::detail return { error::None, RObjectBuilder::template - build(std::forward(retObj), rtl::index_none, isConstCastSafe) + build(std::forward(retObj), std::nullopt, isConstCastSafe) }; } }; diff --git a/ReflectionTemplateLib/detail/inc/TypeId.h b/ReflectionTemplateLib/detail/inc/TypeId.h index 09f4dce6..ce6f8140 100644 --- a/ReflectionTemplateLib/detail/inc/TypeId.h +++ b/ReflectionTemplateLib/detail/inc/TypeId.h @@ -11,16 +11,18 @@ #pragma once +#include #include #include #include namespace rtl { - namespace detail + namespace detail { extern std::size_t generate_unique_id(); + //class to generate unique type-id for a type or combination of types. template struct TypeId; @@ -32,14 +34,25 @@ namespace rtl { //represents '_type' or 'std::nullptr_t' for TypeId<> (empty). using HEAD = _type; + using TAIL = std::nullptr_t; + //'0' represents no type. [Never change, critical.] static constexpr const std::size_t None = 0; static const std::size_t get() { - //statically initialize a unique-id. - static const std::size_t typeId = generate_unique_id(); - return typeId; + if constexpr (!std::is_same_v<_type, std::nullptr_t>) + { + //statically initialize a unique-id. + static const std::size_t TypeId = detail::generate_unique_id(); + return TypeId; + } + return None; + } + + static void get(std::vector& pIds) + { + pIds.push_back(get()); } //returns the type-list as string. @@ -63,11 +76,14 @@ namespace rtl { if constexpr (std::is_same_v<_type, std::string&&>) { return std::string("const std::string&&"); } + if constexpr (std::is_same_v<_type, std::string_view>) { + return std::string("std::string_view"); + } if constexpr (!std::is_same_v<_type, std::nullptr_t>) { return std::string(typeid(_type).name()); } if constexpr (std::is_same_v<_type, std::nullptr_t>) { - return "std::nullptr_t"; + return ""; } else return std::string(); } @@ -84,13 +100,32 @@ namespace rtl { //represents a new list created excluding '_first'. using TAIL = TypeId<_rest...>; + static void get(std::vector& pIds) + { + if constexpr (std::is_same_v) + { + pIds.push_back(TypeId::get()); + } + else { + pIds.push_back(TypeId::get()); + TAIL::get(pIds); + } + } + + //returns the type-list as string. - static std::string toString() + static std::string toString() { const std::string& tailStr = TAIL::toString(); - if (std::is_same::value) { + if (std::is_same::value) { + return ""; + } + else if constexpr (std::is_same::value) { return std::string("std::string") + ", " + tailStr; } + else if constexpr (std::is_same::value) { + return std::string("std::string_view") + ", " + tailStr; + } return (std::string(typeid(HEAD).name()) + ", " + tailStr); } }; From 578589f9c147af11b539fbc4a49289cf05f01428 Mon Sep 17 00:00:00 2001 From: neeraj Date: Mon, 15 Sep 2025 15:48:36 +0530 Subject: [PATCH 05/58] fixed cland/gcc compile error --- ReflectionTemplateLib/access/inc/RObject.hpp | 4 ++-- ReflectionTemplateLib/detail/inc/TypeId.h | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/ReflectionTemplateLib/access/inc/RObject.hpp b/ReflectionTemplateLib/access/inc/RObject.hpp index a34886ea..c692e8ef 100644 --- a/ReflectionTemplateLib/access/inc/RObject.hpp +++ b/ReflectionTemplateLib/access/inc/RObject.hpp @@ -199,7 +199,7 @@ namespace rtl if (m_objectId.m_clonerId.has_value()) { const detail::FunctorId& functorId = m_objectId.m_clonerId.value(); - return traits::Cloner::template forwardCall(functorId, *this, alloc::Heap); + return traits::Cloner::forwardCall(functorId, *this, alloc::Heap); } return { error::CloningDisabled, RObject{} }; } @@ -211,7 +211,7 @@ namespace rtl if (m_objectId.m_clonerId.has_value()) { const detail::FunctorId& functorId = m_objectId.m_clonerId.value(); - return traits::Cloner::template forwardCall(functorId, *this, alloc::Stack); + return traits::Cloner::forwardCall(functorId, *this, alloc::Stack); } return { error::CloningDisabled, RObject{} }; } diff --git a/ReflectionTemplateLib/detail/inc/TypeId.h b/ReflectionTemplateLib/detail/inc/TypeId.h index ce6f8140..2e170f01 100644 --- a/ReflectionTemplateLib/detail/inc/TypeId.h +++ b/ReflectionTemplateLib/detail/inc/TypeId.h @@ -102,7 +102,7 @@ namespace rtl { static void get(std::vector& pIds) { - if constexpr (std::is_same_v) + if constexpr (std::is_same_v) { pIds.push_back(TypeId::get()); } From 2a13e3c13ce6d6f2311f5f1e2179acb737f44bde Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Wed, 17 Sep 2025 16:23:34 +0530 Subject: [PATCH 06/58] New dispatch-design in progress, functor_cache integrated & working. --- CMakeLists.txt | 6 +- CxxTestRegistration/CMakeLists.txt | 4 - CxxTestRegistration/inc/TestMirrorProvider.h | 2 +- .../src/TestMirrorProvider.cpp | 11 +- CxxTestUtils/CMakeLists.txt | 6 +- RTLBenchmarkApp/CMakeLists.txt | 10 -- RTLBenchmarkApp/src/BenchMark.cpp | 2 +- RTLBenchmarkApp/src/ReflectedCall.cpp | 2 +- RTLTestRunApp/CMakeLists.txt | 7 +- .../CxxMirrorTests/CxxMirrorObjectTest.cpp | 3 +- .../CxxMirrorTests/CxxMirrorThreadingTest.cpp | 2 +- .../MyReflectionTests/MyCxxMirrorProvider.cpp | 3 +- .../MyReflectionTests/MyReflectionTests.cpp | 2 +- .../RObjectTests/RObjectReflecting_arrays.cpp | 3 +- .../RObjectTests/RObjectReflecting_bool.cpp | 3 +- .../RObjectTests/RObjectReflecting_char.cpp | 3 +- .../RObjectTests/RObjectReflecting_int.cpp | 3 +- .../RObjectReflecting_stdSharedPtr.cpp | 2 +- .../RObjectReflecting_stdUniquePtr.cpp | 2 +- .../RObjectReflecting_strings.cpp | 3 +- ReflectionTemplateLib/CMakeLists.txt | 25 ++-- .../access/src/CMakeLists.txt | 43 ------ ReflectionTemplateLib/builder/CMakeLists.txt | 26 ---- ReflectionTemplateLib/common/rtl_debug.hpp | 27 ---- .../detail/inc/FunctorCache.h | 58 -------- .../detail/inc/FunctorRegistry.h | 138 ------------------ .../detail/inc/LambdaCache.h | 59 -------- .../detail/inc/LambdaRegistry.h | 132 ----------------- .../detail/src/CMakeLists.txt | 61 -------- ReflectionTemplateLib/rtl/CMakeLists.txt | 21 +++ .../{builder/inc => rtl/builder}/Builder.h | 0 .../{builder/inc => rtl/builder}/Builder.hpp | 2 +- .../rtl/builder/CMakeLists.txt | 27 ++++ .../inc => rtl/builder}/ConstructorBuilder.h | 2 +- .../inc => rtl/builder}/FunctorContainer.h | 24 ++- .../inc => rtl/builder}/MethodContainer.h | 56 +++---- .../inc => rtl/builder}/RObjectBuilder.h | 0 .../inc => rtl/builder}/RObjectBuilder.hpp | 0 .../inc => rtl/builder}/RecordBuilder.h | 0 .../inc => rtl/builder}/RecordBuilder.hpp | 0 .../{builder/inc => rtl/builder}/Reflect.h | 2 +- .../{builder/inc => rtl/builder}/Reflect.hpp | 0 .../inc => rtl/builder}/ReflectionBuilder.h | 0 .../inc => rtl/builder}/ReflectionBuilder.hpp | 0 .../inc => rtl/builder}/SetupConstructor.h | 0 .../inc => rtl/builder}/SetupConstructor.hpp | 32 ++-- .../inc => rtl/builder}/SetupFunction.h | 3 +- .../inc => rtl/builder}/SetupFunction.hpp | 30 ++-- .../{detail/inc => rtl/builder}/SetupMethod.h | 3 +- .../inc => rtl/builder}/SetupMethod.hpp | 85 +++++------ .../rtl/cache/CMakeLists.txt | 12 ++ .../rtl/cache/functor_cache.h | 61 ++++++++ .../rtl/cache/functor_cache_const.h | 61 ++++++++ .../rtl/cache/functor_cache_nonconst.h | 61 ++++++++ .../rtl/cache/lambda_cache.h | 45 ++++++ .../rtl/detail/CMakeLists.txt | 10 ++ .../rtl/detail/inc/CMakeLists.txt | 18 +++ .../detail/inc}/ConversionUtils.h | 0 .../{ => rtl}/detail/inc/CxxReflection.h | 0 .../{ => rtl}/detail/inc/FunctorId.h | 11 +- .../{ => rtl}/detail/inc/RObjExtracter.h | 0 .../{ => rtl}/detail/inc/RObjectId.h | 0 .../{ => rtl}/detail/inc/RObjectUPtr.h | 0 .../{ => rtl}/detail/inc/ReflectCast.h | 0 .../{ => rtl}/detail/inc/ReflectCast.hpp | 2 +- .../{ => rtl}/detail/inc/ReflectCastUtil.h | 0 .../detail/inc}/forward_decls.h | 6 + .../rtl/detail/src/CMakeLists.txt | 11 ++ .../{ => rtl}/detail/src/CxxReflection.cpp | 2 +- .../detail/src/RObjectConverters_string.cpp | 2 +- .../{ => rtl}/detail/src/ReflectCast.cpp | 0 .../rtl/dispatch/CMakeLists.txt | 27 ++++ .../inc => rtl/dispatch}/CallReflector.h | 2 +- .../inc => rtl/dispatch}/FunctionCaller.h | 0 .../inc => rtl/dispatch}/FunctionCaller.hpp | 0 .../inc => rtl/dispatch}/MethodInvoker.h | 0 .../inc => rtl/dispatch}/MethodInvoker.hpp | 0 .../rtl/dispatch/dispatch_interface.h | 80 ++++++++++ ReflectionTemplateLib/rtl/dispatch/functor.h | 43 ++++++ .../rtl/dispatch/functor_const.h | 45 ++++++ .../rtl/dispatch/functor_nonconst.h | 45 ++++++ ReflectionTemplateLib/rtl/dispatch/lambda.h | 58 ++++++++ .../dispatch/lambda_copy_ctor.hpp} | 25 ++-- .../rtl/dispatch/lambda_ctor.hpp | 25 ++++ .../rtl/dispatch/lambda_function.hpp | 70 +++++++++ .../rtl/dispatch/lambda_method_const.hpp | 25 ++++ .../rtl/dispatch/lambda_method_nonconst.hpp | 24 +++ ReflectionTemplateLib/rtl/inc/CMakeLists.txt | 20 +++ .../{access => rtl}/inc/CxxMirror.h | 0 .../{access => rtl}/inc/CxxMirror.hpp | 0 .../{access => rtl}/inc/CxxMirrorToJson.h | 0 .../{access => rtl}/inc/Function.h | 2 +- .../{access => rtl}/inc/Function.hpp | 0 .../{access => rtl}/inc/Method.h | 0 .../{access => rtl}/inc/Method.hpp | 0 .../{access => rtl}/inc/RObject.h | 3 +- .../{access => rtl}/inc/RObject.hpp | 4 +- .../{access => rtl}/inc/Record.h | 2 +- .../{common => rtl/inc}/view.h | 0 .../{common => rtl/inc}/view.hpp | 0 .../{common/RTLibInterface.h => rtl/rtl.h} | 2 - .../Constants.h => rtl/rtl_constants.h} | 2 +- .../error_codes.h => rtl/rtl_errors.h} | 0 .../{common => rtl}/rtl_traits.h | 4 +- .../{detail/inc/TypeId.h => rtl/rtl_typeid.h} | 0 ReflectionTemplateLib/rtl/src/CMakeLists.txt | 11 ++ .../{access => rtl}/src/CxxMirror.cpp | 0 .../{access => rtl}/src/CxxMirrorToJson.cpp | 6 - .../{access => rtl}/src/Function.cpp | 0 109 files changed, 975 insertions(+), 787 deletions(-) delete mode 100644 ReflectionTemplateLib/access/src/CMakeLists.txt delete mode 100644 ReflectionTemplateLib/builder/CMakeLists.txt delete mode 100644 ReflectionTemplateLib/common/rtl_debug.hpp delete mode 100644 ReflectionTemplateLib/detail/inc/FunctorCache.h delete mode 100644 ReflectionTemplateLib/detail/inc/FunctorRegistry.h delete mode 100644 ReflectionTemplateLib/detail/inc/LambdaCache.h delete mode 100644 ReflectionTemplateLib/detail/inc/LambdaRegistry.h delete mode 100644 ReflectionTemplateLib/detail/src/CMakeLists.txt create mode 100644 ReflectionTemplateLib/rtl/CMakeLists.txt rename ReflectionTemplateLib/{builder/inc => rtl/builder}/Builder.h (100%) rename ReflectionTemplateLib/{builder/inc => rtl/builder}/Builder.hpp (99%) create mode 100644 ReflectionTemplateLib/rtl/builder/CMakeLists.txt rename ReflectionTemplateLib/{builder/inc => rtl/builder}/ConstructorBuilder.h (99%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/FunctorContainer.h (84%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/MethodContainer.h (77%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/RObjectBuilder.h (100%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/RObjectBuilder.hpp (100%) rename ReflectionTemplateLib/{builder/inc => rtl/builder}/RecordBuilder.h (100%) rename ReflectionTemplateLib/{builder/inc => rtl/builder}/RecordBuilder.hpp (100%) rename ReflectionTemplateLib/{builder/inc => rtl/builder}/Reflect.h (99%) rename ReflectionTemplateLib/{builder/inc => rtl/builder}/Reflect.hpp (100%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/ReflectionBuilder.h (100%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/ReflectionBuilder.hpp (100%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/SetupConstructor.h (100%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/SetupConstructor.hpp (87%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/SetupFunction.h (97%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/SetupFunction.hpp (83%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/SetupMethod.h (98%) rename ReflectionTemplateLib/{detail/inc => rtl/builder}/SetupMethod.hpp (81%) create mode 100644 ReflectionTemplateLib/rtl/cache/CMakeLists.txt create mode 100644 ReflectionTemplateLib/rtl/cache/functor_cache.h create mode 100644 ReflectionTemplateLib/rtl/cache/functor_cache_const.h create mode 100644 ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h create mode 100644 ReflectionTemplateLib/rtl/cache/lambda_cache.h create mode 100644 ReflectionTemplateLib/rtl/detail/CMakeLists.txt create mode 100644 ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt rename ReflectionTemplateLib/{common => rtl/detail/inc}/ConversionUtils.h (100%) rename ReflectionTemplateLib/{ => rtl}/detail/inc/CxxReflection.h (100%) rename ReflectionTemplateLib/{ => rtl}/detail/inc/FunctorId.h (93%) rename ReflectionTemplateLib/{ => rtl}/detail/inc/RObjExtracter.h (100%) rename ReflectionTemplateLib/{ => rtl}/detail/inc/RObjectId.h (100%) rename ReflectionTemplateLib/{ => rtl}/detail/inc/RObjectUPtr.h (100%) rename ReflectionTemplateLib/{ => rtl}/detail/inc/ReflectCast.h (100%) rename ReflectionTemplateLib/{ => rtl}/detail/inc/ReflectCast.hpp (99%) rename ReflectionTemplateLib/{ => rtl}/detail/inc/ReflectCastUtil.h (100%) rename ReflectionTemplateLib/{common => rtl/detail/inc}/forward_decls.h (91%) create mode 100644 ReflectionTemplateLib/rtl/detail/src/CMakeLists.txt rename ReflectionTemplateLib/{ => rtl}/detail/src/CxxReflection.cpp (99%) rename ReflectionTemplateLib/{ => rtl}/detail/src/RObjectConverters_string.cpp (99%) rename ReflectionTemplateLib/{ => rtl}/detail/src/ReflectCast.cpp (100%) create mode 100644 ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt rename ReflectionTemplateLib/{detail/inc => rtl/dispatch}/CallReflector.h (99%) rename ReflectionTemplateLib/{detail/inc => rtl/dispatch}/FunctionCaller.h (100%) rename ReflectionTemplateLib/{detail/inc => rtl/dispatch}/FunctionCaller.hpp (100%) rename ReflectionTemplateLib/{detail/inc => rtl/dispatch}/MethodInvoker.h (100%) rename ReflectionTemplateLib/{detail/inc => rtl/dispatch}/MethodInvoker.hpp (100%) create mode 100644 ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h create mode 100644 ReflectionTemplateLib/rtl/dispatch/functor.h create mode 100644 ReflectionTemplateLib/rtl/dispatch/functor_const.h create mode 100644 ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h create mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda.h rename ReflectionTemplateLib/{detail/inc/LambdaBridge.h => rtl/dispatch/lambda_copy_ctor.hpp} (66%) create mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp create mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp create mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp create mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp create mode 100644 ReflectionTemplateLib/rtl/inc/CMakeLists.txt rename ReflectionTemplateLib/{access => rtl}/inc/CxxMirror.h (100%) rename ReflectionTemplateLib/{access => rtl}/inc/CxxMirror.hpp (100%) rename ReflectionTemplateLib/{access => rtl}/inc/CxxMirrorToJson.h (100%) rename ReflectionTemplateLib/{access => rtl}/inc/Function.h (99%) rename ReflectionTemplateLib/{access => rtl}/inc/Function.hpp (100%) rename ReflectionTemplateLib/{access => rtl}/inc/Method.h (100%) rename ReflectionTemplateLib/{access => rtl}/inc/Method.hpp (100%) rename ReflectionTemplateLib/{access => rtl}/inc/RObject.h (99%) rename ReflectionTemplateLib/{access => rtl}/inc/RObject.hpp (97%) rename ReflectionTemplateLib/{access => rtl}/inc/Record.h (99%) rename ReflectionTemplateLib/{common => rtl/inc}/view.h (100%) rename ReflectionTemplateLib/{common => rtl/inc}/view.hpp (100%) rename ReflectionTemplateLib/{common/RTLibInterface.h => rtl/rtl.h} (97%) rename ReflectionTemplateLib/{common/Constants.h => rtl/rtl_constants.h} (99%) rename ReflectionTemplateLib/{common/error_codes.h => rtl/rtl_errors.h} (100%) rename ReflectionTemplateLib/{common => rtl}/rtl_traits.h (99%) rename ReflectionTemplateLib/{detail/inc/TypeId.h => rtl/rtl_typeid.h} (100%) create mode 100644 ReflectionTemplateLib/rtl/src/CMakeLists.txt rename ReflectionTemplateLib/{access => rtl}/src/CxxMirror.cpp (100%) rename ReflectionTemplateLib/{access => rtl}/src/CxxMirrorToJson.cpp (94%) rename ReflectionTemplateLib/{access => rtl}/src/Function.cpp (100%) diff --git a/CMakeLists.txt b/CMakeLists.txt index 0500cf1d..5c611b4f 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -6,9 +6,9 @@ project(CxxReflectionProject) set(CMAKE_RUNTIME_OUTPUT_DIRECTORY "${CMAKE_SOURCE_DIR}/bin") # Add the subdirectories +add_subdirectory(ReflectionTemplateLib) add_subdirectory(CxxTestRegistration) -add_subdirectory(RTLTestRunApp) -add_subdirectory(RTLBenchmarkApp) add_subdirectory(CxxTestProps) add_subdirectory(CxxTestUtils) -add_subdirectory(ReflectionTemplateLib) \ No newline at end of file +add_subdirectory(RTLTestRunApp) +add_subdirectory(RTLBenchmarkApp) \ No newline at end of file diff --git a/CxxTestRegistration/CMakeLists.txt b/CxxTestRegistration/CMakeLists.txt index 96b0a6a3..fe4d4a19 100644 --- a/CxxTestRegistration/CMakeLists.txt +++ b/CxxTestRegistration/CMakeLists.txt @@ -15,10 +15,6 @@ ADD_LIBRARY(${PROJECT_NAME} STATIC "") INCLUDE_DIRECTORIES(inc) INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/CxxTestUtils/inc") INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/CxxTestProps/inc") -INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/common") -INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/detail/inc") -INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/access/inc") -INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/builder/inc") TARGET_LINK_LIBRARIES(${CXX_LIB_NAME} ReflectionTemplateLib) diff --git a/CxxTestRegistration/inc/TestMirrorProvider.h b/CxxTestRegistration/inc/TestMirrorProvider.h index 42072a54..d71113f4 100644 --- a/CxxTestRegistration/inc/TestMirrorProvider.h +++ b/CxxTestRegistration/inc/TestMirrorProvider.h @@ -1,6 +1,6 @@ #pragma once -#include "RTLibInterface.h" +#include namespace test_mirror { diff --git a/CxxTestRegistration/src/TestMirrorProvider.cpp b/CxxTestRegistration/src/TestMirrorProvider.cpp index db44c78e..5388abea 100644 --- a/CxxTestRegistration/src/TestMirrorProvider.cpp +++ b/CxxTestRegistration/src/TestMirrorProvider.cpp @@ -202,9 +202,14 @@ namespace test_mirror rtl::type().member().methodStatic(animal::str_updateZooKeeper).build(&Animal::updateZooKeeper), #if defined(__GNUC__) && !defined(__clang__) - /* GCC fails to automatically identify the correct overloaded functor to pick. (non-const-lvalue-ref & rvalue as argument) - we need to explicitly cast the functor like, static_cast(&Animal::setAnimalName). - */ rtl::type().member() + /* + GCC fails to automatically resolve the correct overloaded functor + when both a non-const lvalue reference and an rvalue overload exist. + To disambiguate, explicitly cast the member function pointer, e.g.: + + static_cast(&Animal::setAnimalName); + */ + rtl::type().member() .method(animal::str_setAnimalName) .build(static_cast(&Animal::setAnimalName)), //overloaded method, taking non-const lvalue reference as argument. diff --git a/CxxTestUtils/CMakeLists.txt b/CxxTestUtils/CMakeLists.txt index b43de122..bca425cc 100644 --- a/CxxTestUtils/CMakeLists.txt +++ b/CxxTestUtils/CMakeLists.txt @@ -14,8 +14,8 @@ ADD_LIBRARY(${PROJECT_NAME} STATIC "") INCLUDE_DIRECTORIES(inc) INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/CxxTestProps/inc") -INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/common") -INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/access/inc") -INCLUDE_DIRECTORIES("${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/detail/inc") + +TARGET_LINK_LIBRARIES(${CXX_LIB_NAME} ReflectionTemplateLib) + # Add the source directory INCLUDE(src/CMakeLists.txt) \ No newline at end of file diff --git a/RTLBenchmarkApp/CMakeLists.txt b/RTLBenchmarkApp/CMakeLists.txt index ae302c8c..72cd7492 100644 --- a/RTLBenchmarkApp/CMakeLists.txt +++ b/RTLBenchmarkApp/CMakeLists.txt @@ -25,16 +25,6 @@ if(NOT benchmark_POPULATED) add_subdirectory(${benchmark_SOURCE_DIR} ${benchmark_BINARY_DIR} EXCLUDE_FROM_ALL) endif() -# =============================== -# Common Include Paths -# =============================== -set(RTL_INCLUDE_DIRS - inc - "${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/common" - "${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/detail/inc" - "${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/access/inc" - "${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/builder/inc" -) # =============================== # Test Executable diff --git a/RTLBenchmarkApp/src/BenchMark.cpp b/RTLBenchmarkApp/src/BenchMark.cpp index 72b66cc6..350617aa 100644 --- a/RTLBenchmarkApp/src/BenchMark.cpp +++ b/RTLBenchmarkApp/src/BenchMark.cpp @@ -5,7 +5,7 @@ #include #include "BenchMark.h" -#include "RTLibInterface.h" +#include namespace bm diff --git a/RTLBenchmarkApp/src/ReflectedCall.cpp b/RTLBenchmarkApp/src/ReflectedCall.cpp index 099d3c44..4c2bf8ac 100644 --- a/RTLBenchmarkApp/src/ReflectedCall.cpp +++ b/RTLBenchmarkApp/src/ReflectedCall.cpp @@ -2,7 +2,7 @@ #include #include "ReflectedCall.h" -#include "RTLibInterface.h" +#include #include "BenchMark.h" namespace cxx diff --git a/RTLTestRunApp/CMakeLists.txt b/RTLTestRunApp/CMakeLists.txt index 3b2177eb..3b88d6c2 100644 --- a/RTLTestRunApp/CMakeLists.txt +++ b/RTLTestRunApp/CMakeLists.txt @@ -31,10 +31,6 @@ set(RTL_INCLUDE_DIRS inc "${CMAKE_SOURCE_DIR}/CxxTestUtils/inc" "${CMAKE_SOURCE_DIR}/CxxTestRegistration/inc" - "${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/common" - "${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/detail/inc" - "${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/access/inc" - "${CMAKE_SOURCE_DIR}/ReflectionTemplateLib/builder/inc" ) # =============================== @@ -42,7 +38,6 @@ set(RTL_INCLUDE_DIRS # =============================== set(CXX_EXE_NAME RTLTestRunApp) -# Add all test sources (either glob or include your src/CMakeLists.txt) file(GLOB_RECURSE TEST_SOURCES CONFIGURE_DEPENDS src/*.cpp) add_executable(${CXX_EXE_NAME} ${TEST_SOURCES}) @@ -56,8 +51,10 @@ target_link_libraries(${CXX_EXE_NAME} GTest::gtest_main ) + # =============================== # GoogleTest Integration # =============================== + include(GoogleTest) gtest_discover_tests(${CXX_EXE_NAME}) diff --git a/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp b/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp index 57f445ea..d6f62f6e 100644 --- a/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp +++ b/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp @@ -1,9 +1,8 @@ #include - #include +#include -#include "RTLibInterface.h" #include "CxxMirrorToJson.h" namespace diff --git a/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorThreadingTest.cpp b/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorThreadingTest.cpp index b340a9c0..c3246388 100644 --- a/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorThreadingTest.cpp +++ b/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorThreadingTest.cpp @@ -3,6 +3,7 @@ #include #include #include +#include #include "../../CxxTestProps/inc/Date.h" #include "../../CxxTestProps/inc/Book.h" @@ -18,7 +19,6 @@ #include "TestUtilsAnimal.h" #include "GlobalTestUtils.h" -#include "RTLibInterface.h" #include "CxxMirrorThreadingTest.h" using namespace test_utils; diff --git a/RTLTestRunApp/src/MyReflectionTests/MyCxxMirrorProvider.cpp b/RTLTestRunApp/src/MyReflectionTests/MyCxxMirrorProvider.cpp index d406e941..1fa8fe82 100644 --- a/RTLTestRunApp/src/MyReflectionTests/MyCxxMirrorProvider.cpp +++ b/RTLTestRunApp/src/MyReflectionTests/MyCxxMirrorProvider.cpp @@ -1,5 +1,6 @@ -#include "RTLibInterface.h" +#include + #include "MyReflectingType.h" namespace my_type diff --git a/RTLTestRunApp/src/MyReflectionTests/MyReflectionTests.cpp b/RTLTestRunApp/src/MyReflectionTests/MyReflectionTests.cpp index 349c1836..b076085f 100644 --- a/RTLTestRunApp/src/MyReflectionTests/MyReflectionTests.cpp +++ b/RTLTestRunApp/src/MyReflectionTests/MyReflectionTests.cpp @@ -1,7 +1,7 @@ #include +#include -#include "RTLibInterface.h" #include "MyReflectingType.h" using namespace my_type; diff --git a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_arrays.cpp b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_arrays.cpp index 1a1753c6..692c85ba 100644 --- a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_arrays.cpp +++ b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_arrays.cpp @@ -14,8 +14,7 @@ */ #include - -#include "RTLibInterface.h" +#include using namespace rtl; diff --git a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_bool.cpp b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_bool.cpp index 914b0dc7..71396728 100644 --- a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_bool.cpp +++ b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_bool.cpp @@ -1,7 +1,6 @@  #include - -#include "RTLibInterface.h" +#include using namespace rtl; diff --git a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_char.cpp b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_char.cpp index 5acfa96e..d8d5da7a 100644 --- a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_char.cpp +++ b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_char.cpp @@ -1,7 +1,6 @@  #include - -#include "RTLibInterface.h" +#include using namespace rtl; diff --git a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_int.cpp b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_int.cpp index 57b8cd6c..6abb91e8 100644 --- a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_int.cpp +++ b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_int.cpp @@ -1,7 +1,6 @@  #include - -#include "RTLibInterface.h" +#include using namespace rtl; diff --git a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdSharedPtr.cpp b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdSharedPtr.cpp index 5b71d321..6a483e8d 100644 --- a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdSharedPtr.cpp +++ b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdSharedPtr.cpp @@ -1,9 +1,9 @@ #include #include +#include #include "Node.h" -#include "RTLibInterface.h" using namespace test_utils; using namespace rtl; diff --git a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdUniquePtr.cpp b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdUniquePtr.cpp index 5ff37e92..a43a8cd9 100644 --- a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdUniquePtr.cpp +++ b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_stdUniquePtr.cpp @@ -1,9 +1,9 @@ #include #include +#include #include "Node.h" -#include "RTLibInterface.h" using namespace test_utils; using namespace rtl; diff --git a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_strings.cpp b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_strings.cpp index 21d27632..c3ff3713 100644 --- a/RTLTestRunApp/src/RObjectTests/RObjectReflecting_strings.cpp +++ b/RTLTestRunApp/src/RObjectTests/RObjectReflecting_strings.cpp @@ -1,7 +1,6 @@ #include - -#include "RTLibInterface.h" +#include using namespace rtl; diff --git a/ReflectionTemplateLib/CMakeLists.txt b/ReflectionTemplateLib/CMakeLists.txt index 894d02b8..24defcf1 100644 --- a/ReflectionTemplateLib/CMakeLists.txt +++ b/ReflectionTemplateLib/CMakeLists.txt @@ -1,8 +1,5 @@ -# CMakeLists.txt for ReflectionTemplateLib - cmake_minimum_required(VERSION 3.20) -# Project definition project(ReflectionTemplateLib LANGUAGES CXX) # Require C++20 @@ -10,19 +7,21 @@ set(CMAKE_CXX_STANDARD 20) set(CMAKE_CXX_STANDARD_REQUIRED ON) set(CMAKE_CXX_EXTENSIONS OFF) -# Library target +# Library target (static or shared) add_library(${PROJECT_NAME} STATIC) -# Public include directories +# Public include paths for this library target_include_directories(${PROJECT_NAME} PUBLIC - ${CMAKE_CURRENT_SOURCE_DIR}/common - ${CMAKE_CURRENT_SOURCE_DIR}/detail/inc - ${CMAKE_CURRENT_SOURCE_DIR}/access/inc - ${CMAKE_CURRENT_SOURCE_DIR}/builder/inc + ${CMAKE_CURRENT_SOURCE_DIR} + ${CMAKE_CURRENT_SOURCE_DIR}/rtl/builder + ${CMAKE_CURRENT_SOURCE_DIR}/rtl/cache + ${CMAKE_CURRENT_SOURCE_DIR}/rtl/detail + ${CMAKE_CURRENT_SOURCE_DIR}/rtl/dispatch + ${CMAKE_CURRENT_SOURCE_DIR}/rtl/registry + ${CMAKE_CURRENT_SOURCE_DIR}/rtl/inc + ${CMAKE_CURRENT_SOURCE_DIR}/rtl ) -# Add subdirectories for sources -add_subdirectory(detail/src) -add_subdirectory(access/src) -add_subdirectory(builder) \ No newline at end of file +# Add subdirectories +add_subdirectory(rtl) \ No newline at end of file diff --git a/ReflectionTemplateLib/access/src/CMakeLists.txt b/ReflectionTemplateLib/access/src/CMakeLists.txt deleted file mode 100644 index c8935285..00000000 --- a/ReflectionTemplateLib/access/src/CMakeLists.txt +++ /dev/null @@ -1,43 +0,0 @@ -# Create a variable containing the source files for your target -set(LOCAL_SOURCES - "${CMAKE_CURRENT_LIST_DIR}/CxxMirror.cpp" - "${CMAKE_CURRENT_LIST_DIR}/CxxMirrorToJson.cpp" - "${CMAKE_CURRENT_LIST_DIR}/Function.cpp" -) - -SET(COMMON_HEADERS - - "${PROJECT_SOURCE_DIR}/common/view.h" - "${PROJECT_SOURCE_DIR}/common/view.hpp" - "${PROJECT_SOURCE_DIR}/common/Constants.h" - "${PROJECT_SOURCE_DIR}/common/rtl_traits.h" - "${PROJECT_SOURCE_DIR}/common/error_codes.h" - "${PROJECT_SOURCE_DIR}/common/forward_decls.h" - "${PROJECT_SOURCE_DIR}/common/ConversionUtils.h" - "${PROJECT_SOURCE_DIR}/common/RTLibInterface.h" -) - -SET(LOCAL_HEADERS - "${PROJECT_SOURCE_DIR}/access/inc/CxxMirror.h" - "${PROJECT_SOURCE_DIR}/access/inc/CxxMirror.hpp" - "${PROJECT_SOURCE_DIR}/access/inc/CxxMirrorToJson.h" - "${PROJECT_SOURCE_DIR}/access/inc/Function.h" - "${PROJECT_SOURCE_DIR}/access/inc/Function.hpp" - "${PROJECT_SOURCE_DIR}/access/inc/Method.h" - "${PROJECT_SOURCE_DIR}/access/inc/Method.hpp" - "${PROJECT_SOURCE_DIR}/access/inc/Record.h" - "${PROJECT_SOURCE_DIR}/access/inc/RObject.h" - "${PROJECT_SOURCE_DIR}/access/inc/RObject.hpp" -) - -# Add any additional source files if needed -target_sources(ReflectionTemplateLib - PRIVATE - "${LOCAL_HEADERS}" - "${COMMON_HEADERS}" - "${LOCAL_SOURCES}" -) - - -SOURCE_GROUP("Source Files\\Access" FILES ${LOCAL_SOURCES}) -SOURCE_GROUP("Header Files\\Access" FILES ${LOCAL_HEADERS}) \ No newline at end of file diff --git a/ReflectionTemplateLib/builder/CMakeLists.txt b/ReflectionTemplateLib/builder/CMakeLists.txt deleted file mode 100644 index 379e654e..00000000 --- a/ReflectionTemplateLib/builder/CMakeLists.txt +++ /dev/null @@ -1,26 +0,0 @@ -# Create a variable containing the source files for your target - -SET(COMMON_HEADERS - "${PROJECT_SOURCE_DIR}/common/rtl_traits.h" - "${PROJECT_SOURCE_DIR}/common/error_codes.h" - "${PROJECT_SOURCE_DIR}/common/forward_decls.h" -) - -SET(LOCAL_HEADERS - "${CMAKE_CURRENT_LIST_DIR}/inc/ConstructorBuilder.h" - "${CMAKE_CURRENT_LIST_DIR}/inc/Builder.h" - "${CMAKE_CURRENT_LIST_DIR}/inc/Builder.hpp" - "${CMAKE_CURRENT_LIST_DIR}/inc/RecordBuilder.h" - "${CMAKE_CURRENT_LIST_DIR}/inc/RecordBuilder.hpp" - "${CMAKE_CURRENT_LIST_DIR}/inc/Reflect.h" - "${CMAKE_CURRENT_LIST_DIR}/inc/Reflect.hpp" -) - -# Add any additional source files if needed -target_sources(ReflectionTemplateLib - PRIVATE - "${LOCAL_HEADERS}" - "${COMMON_HEADERS}" -) - -SOURCE_GROUP("Header Files\\Builder" FILES ${LOCAL_HEADERS}) \ No newline at end of file diff --git a/ReflectionTemplateLib/common/rtl_debug.hpp b/ReflectionTemplateLib/common/rtl_debug.hpp deleted file mode 100644 index 4d2b4739..00000000 --- a/ReflectionTemplateLib/common/rtl_debug.hpp +++ /dev/null @@ -1,27 +0,0 @@ -#pragma once -// #include - -#ifdef RTL_DEBUG - -// Runs arbitrary code safely in Debug builds (single-statement safe) -#define RTL_DEBUG_ONLY(code) do { code } while(0) - -// Simple debug log -// #define RTL_LOG(msg) do { std::cout << "[RTL-DEBUG] " << msg << '\n'; } while(0) - -// Exception-free assert: if condition fails, prints message and returns error code -// #define RTL_ASSERT(cond, err_code) do { \ -// if (!(cond)) { \ -// std::cerr << "[RTL-ASSERT] " #cond " failed!\n"; \ -// return err_code; \ -// } \ -// } while(0) - -#else - -// Release builds: completely stripped out -#define RTL_DEBUG_ONLY(code) do {} while(0) -// #define RTL_LOG(msg) do {} while(0) -// #define RTL_ASSERT(cond, err_code) do {} while(0) - -#endif diff --git a/ReflectionTemplateLib/detail/inc/FunctorCache.h b/ReflectionTemplateLib/detail/inc/FunctorCache.h deleted file mode 100644 index 1a89a0cd..00000000 --- a/ReflectionTemplateLib/detail/inc/FunctorCache.h +++ /dev/null @@ -1,58 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include "Constants.h" -#include "FunctorRegistry.h" - - -namespace rtl::detail -{ - template - struct functor_cache; -} - -namespace rtl::detail -{ - template<> - struct functor_cache - { - template - static functor_registry& get() - { - static functor_registry functors; - return functors; - } - }; - - template<> - struct functor_cache - { - template - static functor_registry_m& get() - { - static functor_registry_m functors; - return functors; - } - }; - - template<> - struct functor_cache - { - template - static functor_registry_m& get() - { - static functor_registry_m functors; - return functors; - } - }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/FunctorRegistry.h b/ReflectionTemplateLib/detail/inc/FunctorRegistry.h deleted file mode 100644 index 8ef91ea8..00000000 --- a/ReflectionTemplateLib/detail/inc/FunctorRegistry.h +++ /dev/null @@ -1,138 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include - -#include "Constants.h" -#include "forward_decls.h" - - -namespace rtl::detail -{ - class functor_hop {}; -} - - -namespace rtl::detail -{ - template - class functor_registry: public functor_hop - { - using functor_t = return_t(*)(signature_ts...); - - std::vector> m_functors; - - public: - - const std::vector>& get() { - return m_functors; - } - - functor_t operator[](std::size_t index) { - return m_functors[index].first; - } - - void push(functor_t fptr, std::size_t lambda_index) { - m_functors.emplace_back(fptr, lambda_index); - } - - std::pair find(functor_t fptr) - { - //linear search, efficient for small set. - for (int index = 0; index < m_functors.size(); index++) { - if (m_functors[index].first == fptr) { - return { index, m_functors[index].second }; - } - } - return { rtl::index_none, rtl::index_none }; - } - }; -} - - -namespace rtl::detail -{ - template - class functor_registry_m; - - template - class functor_registry_m : public functor_hop - { - using functor_t = return_t(record_t::*)(signature_ts...); - - std::vector> m_functors; - - public: - - const std::vector>& get() { - return m_functors; - } - - - functor_t operator[](std::size_t index) { - return m_functors[index].first; - } - - void push(functor_t fptr, std::size_t lambda_index) { - m_functors.emplace_back(fptr, lambda_index); - } - - std::pair find(functor_t fptr) - { - //linear search, efficient for small set. - for (int index = 0; index < m_functors.size(); index++) { - if (m_functors[index].first == fptr) { - return { index, m_functors[index].second }; - } - } - return { rtl::index_none, rtl::index_none }; - } - }; -} - - -namespace rtl::detail -{ - template - class functor_registry_m : public functor_hop - { - using functor_t = return_t(record_t::*)(signature_ts...) const; - - std::vector> m_functors; - - public: - - const std::vector>& get() { - return m_functors; - } - - functor_t operator[](std::size_t index) { - return m_functors[index].first; - } - - void push(functor_t fptr, std::size_t lambda_index) { - m_functors.emplace_back(fptr, lambda_index); - } - - std::pair find(functor_t fptr) - { - //linear search, efficient for small set. - for (int index = 0; index < m_functors.size(); index++) { - if (m_functors[index].first == fptr) { - return { index, m_functors[index].second }; - } - } - return { rtl::index_none, rtl::index_none }; - } - }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/LambdaCache.h b/ReflectionTemplateLib/detail/inc/LambdaCache.h deleted file mode 100644 index 8c5daa5c..00000000 --- a/ReflectionTemplateLib/detail/inc/LambdaCache.h +++ /dev/null @@ -1,59 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include "LambdaRegistry.h" - - -namespace rtl::detail -{ - template - struct lambda_cache; -} - -namespace rtl::detail -{ - template<> - struct lambda_cache - { - template - static lambda_registry& get() - { - static lambda_registry registry; - return registry; - } - }; - - - template<> - struct lambda_cache - { - template - static lambda_registry& get() - { - static lambda_registry registry; - return registry; - } - }; - - - template<> - struct lambda_cache - { - template - static lambda_registry& get() - { - static lambda_registry registry; - return registry; - } - }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/LambdaRegistry.h b/ReflectionTemplateLib/detail/inc/LambdaRegistry.h deleted file mode 100644 index 58b15385..00000000 --- a/ReflectionTemplateLib/detail/inc/LambdaRegistry.h +++ /dev/null @@ -1,132 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include "LambdaBridge.h" - -#include -#include -#include - -#include "TypeId.h" -#include "Constants.h" -#include "FunctorRegistry.h" - - -namespace rtl::detail -{ - class lambda_hop { - public: - - std::size_t m_signatureId = TypeId<>::None; - std::vector m_argsId; - }; -} - - -namespace rtl::detail -{ - template - class lambda_registry; - - template - class lambda_registry : public lambda_hop - { - using lambda_t = std::function; - - std::vector lambda_table; - - std::vector m_functors; - - public: - - lambda_registry() - { - m_signatureId = TypeId>::get(); - TypeId::get(m_argsId); - } - - GETTER_CREF(std::vector, , lambda_table) - - void push(const lambda_t& lambda) - { - lambda_table.push_back(lambda); - } - - Return operator()(std::size_t index, signature_ts&&...params) - { - return lambda_table[index](m_functors[index], index, std::forward(params)...); - } - }; - - - template - class lambda_registry : public lambda_hop - { - using lambda_t = std::function ; - - std::vector lambda_table; - - std::vector m_functors; - - public: - - lambda_registry() - { - m_signatureId = TypeId>::get(); - TypeId::get(m_argsId); - } - - GETTER_CREF(std::vector, , lambda_table) - - void push(const lambda_t& lambda) - { - lambda_table.push_back(lambda); - } - - Return operator()(std::size_t index, signature_ts&&...params) - { - return lambda_table[index](m_functors[index], index, std::forward(params)...); - } - }; - - - template - class lambda_registry : public lambda_hop - { - using lambda_t = std::function ; - - std::vector lambda_table; - - std::vector m_functors; - - public: - - lambda_registry() - { - m_signatureId = TypeId>::get(); - TypeId::get(m_argsId); - } - - GETTER_CREF(std::vector, , lambda_table) - - void push(const lambda_t& lambda) - { - lambda_table.push_back(lambda); - } - - Return operator()(std::size_t index, signature_ts&&...params) - { - return lambda_table[index](m_functors[index], index, std::forward(params)...); - } - }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/src/CMakeLists.txt b/ReflectionTemplateLib/detail/src/CMakeLists.txt deleted file mode 100644 index d5f37592..00000000 --- a/ReflectionTemplateLib/detail/src/CMakeLists.txt +++ /dev/null @@ -1,61 +0,0 @@ -# Create a variable containing the source files for your target -set(LOCAL_SOURCES - "${CMAKE_CURRENT_LIST_DIR}/CxxReflection.cpp" - "${CMAKE_CURRENT_LIST_DIR}/ReflectCast.cpp" - "${CMAKE_CURRENT_LIST_DIR}/RObjectConverters_string.cpp" -) - - -SET(COMMON_HEADERS - - "${PROJECT_SOURCE_DIR}/common/rtl_traits.h" - "${PROJECT_SOURCE_DIR}/common/error_codes.h" - "${PROJECT_SOURCE_DIR}/common/forward_decls.h" -) - -SET(LOCAL_HEADERS - - "${PROJECT_SOURCE_DIR}/detail/inc/LambdaCache.h" - "${PROJECT_SOURCE_DIR}/detail/inc/FunctorCache.h" - "${PROJECT_SOURCE_DIR}/detail/inc/LambdaBridge.h" - "${PROJECT_SOURCE_DIR}/detail/inc/LambdaRegistry.h" - "${PROJECT_SOURCE_DIR}/detail/inc/FunctorRegistry.h" - "${PROJECT_SOURCE_DIR}/detail/inc/CallReflector.h" - "${PROJECT_SOURCE_DIR}/detail/inc/CxxReflection.h" - "${PROJECT_SOURCE_DIR}/detail/inc/FunctionCaller.h" - "${PROJECT_SOURCE_DIR}/detail/inc/FunctionCaller.hpp" - "${PROJECT_SOURCE_DIR}/detail/inc/MethodInvoker.h" - "${PROJECT_SOURCE_DIR}/detail/inc/MethodInvoker.hpp" - "${PROJECT_SOURCE_DIR}/detail/inc/FunctorContainer.h" - "${PROJECT_SOURCE_DIR}/detail/inc/FunctorId.h" - "${PROJECT_SOURCE_DIR}/detail/inc/RObjectId.h" - "${PROJECT_SOURCE_DIR}/detail/inc/MethodContainer.h" - "${PROJECT_SOURCE_DIR}/detail/inc/ReflectCast.h" - "${PROJECT_SOURCE_DIR}/detail/inc/ReflectCast.hpp" - "${PROJECT_SOURCE_DIR}/detail/inc/ReflectCastUtil.h" - "${PROJECT_SOURCE_DIR}/detail/inc/ReflectionBuilder.h" - "${PROJECT_SOURCE_DIR}/detail/inc/ReflectionBuilder.hpp" - "${PROJECT_SOURCE_DIR}/detail/inc/SetupConstructor.h" - "${PROJECT_SOURCE_DIR}/detail/inc/SetupConstructor.hpp" - "${PROJECT_SOURCE_DIR}/detail/inc/SetupFunction.h" - "${PROJECT_SOURCE_DIR}/detail/inc/SetupFunction.hpp" - "${PROJECT_SOURCE_DIR}/detail/inc/SetupMethod.h" - "${PROJECT_SOURCE_DIR}/detail/inc/SetupMethod.hpp" - "${PROJECT_SOURCE_DIR}/detail/inc/TypeId.h" - "${PROJECT_SOURCE_DIR}/detail/inc/RObjectUPtr.h" - "${PROJECT_SOURCE_DIR}/detail/inc/RObjExtracter.h" - "${PROJECT_SOURCE_DIR}/detail/inc/RObjectBuilder.h" - "${PROJECT_SOURCE_DIR}/detail/inc/RObjectBuilder.hpp" -) - - -# Add any additional source files if needed -target_sources(ReflectionTemplateLib - PRIVATE - "${LOCAL_HEADERS}" - "${LOCAL_SOURCES}" -) - - -SOURCE_GROUP("Source Files\\Detail" FILES ${LOCAL_SOURCES}) -SOURCE_GROUP("Header Files\\Detail" FILES ${LOCAL_HEADERS}) \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/CMakeLists.txt b/ReflectionTemplateLib/rtl/CMakeLists.txt new file mode 100644 index 00000000..0f97298d --- /dev/null +++ b/ReflectionTemplateLib/rtl/CMakeLists.txt @@ -0,0 +1,21 @@ +# ReflectionTemplateLibrary-CPP/ReflectionTemplateLib/rtl/CMakeLists.txt + +# Top-level headers in rtl/ (absolute paths) +set(LOCAL_HEADERS + "${CMAKE_CURRENT_SOURCE_DIR}/rtl.h" + "${CMAKE_CURRENT_SOURCE_DIR}/rtl_constants.h" + "${CMAKE_CURRENT_SOURCE_DIR}/rtl_errors.h" + "${CMAKE_CURRENT_SOURCE_DIR}/rtl_traits.h" + "${CMAKE_CURRENT_SOURCE_DIR}/rtl_typeid.h" +) + +target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) +source_group("Header Files\\RTL" FILES ${LOCAL_HEADERS}) + +# Add subdirectories +add_subdirectory(inc) +add_subdirectory(src) +add_subdirectory(builder) +add_subdirectory(cache) +add_subdirectory(detail) +add_subdirectory(dispatch) \ No newline at end of file diff --git a/ReflectionTemplateLib/builder/inc/Builder.h b/ReflectionTemplateLib/rtl/builder/Builder.h similarity index 100% rename from ReflectionTemplateLib/builder/inc/Builder.h rename to ReflectionTemplateLib/rtl/builder/Builder.h diff --git a/ReflectionTemplateLib/builder/inc/Builder.hpp b/ReflectionTemplateLib/rtl/builder/Builder.hpp similarity index 99% rename from ReflectionTemplateLib/builder/inc/Builder.hpp rename to ReflectionTemplateLib/rtl/builder/Builder.hpp index ee74df9c..a343fbd8 100644 --- a/ReflectionTemplateLib/builder/inc/Builder.hpp +++ b/ReflectionTemplateLib/rtl/builder/Builder.hpp @@ -11,7 +11,7 @@ #pragma once -#include "TypeId.h" +#include "rtl_typeid.h" #include "Builder.h" #include "ReflectionBuilder.hpp" diff --git a/ReflectionTemplateLib/rtl/builder/CMakeLists.txt b/ReflectionTemplateLib/rtl/builder/CMakeLists.txt new file mode 100644 index 00000000..03414d6b --- /dev/null +++ b/ReflectionTemplateLib/rtl/builder/CMakeLists.txt @@ -0,0 +1,27 @@ +# ReflectionTemplateLibrary-CPP/ReflectionTemplateLib/builder/CMakeLists.txt + +# Collect all headers in builder/ (absolute paths) +set(LOCAL_HEADERS + "${CMAKE_CURRENT_SOURCE_DIR}/Builder.h" + "${CMAKE_CURRENT_SOURCE_DIR}/Builder.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/ConstructorBuilder.h" + "${CMAKE_CURRENT_SOURCE_DIR}/FunctorContainer.h" + "${CMAKE_CURRENT_SOURCE_DIR}/MethodContainer.h" + "${CMAKE_CURRENT_SOURCE_DIR}/RecordBuilder.h" + "${CMAKE_CURRENT_SOURCE_DIR}/RecordBuilder.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/Reflect.h" + "${CMAKE_CURRENT_SOURCE_DIR}/Reflect.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/ReflectionBuilder.h" + "${CMAKE_CURRENT_SOURCE_DIR}/ReflectionBuilder.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/RObjectBuilder.h" + "${CMAKE_CURRENT_SOURCE_DIR}/RObjectBuilder.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/SetupConstructor.h" + "${CMAKE_CURRENT_SOURCE_DIR}/SetupConstructor.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/SetupFunction.h" + "${CMAKE_CURRENT_SOURCE_DIR}/SetupFunction.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/SetupMethod.h" + "${CMAKE_CURRENT_SOURCE_DIR}/SetupMethod.hpp" +) + +target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) +source_group("Header Files\\Builder" FILES ${LOCAL_HEADERS}) \ No newline at end of file diff --git a/ReflectionTemplateLib/builder/inc/ConstructorBuilder.h b/ReflectionTemplateLib/rtl/builder/ConstructorBuilder.h similarity index 99% rename from ReflectionTemplateLib/builder/inc/ConstructorBuilder.h rename to ReflectionTemplateLib/rtl/builder/ConstructorBuilder.h index 94e4ba3f..5031b02e 100644 --- a/ReflectionTemplateLib/builder/inc/ConstructorBuilder.h +++ b/ReflectionTemplateLib/rtl/builder/ConstructorBuilder.h @@ -11,7 +11,7 @@ #pragma once -#include "Constants.h" +#include "rtl_constants.h" namespace rtl { diff --git a/ReflectionTemplateLib/detail/inc/FunctorContainer.h b/ReflectionTemplateLib/rtl/builder/FunctorContainer.h similarity index 84% rename from ReflectionTemplateLib/detail/inc/FunctorContainer.h rename to ReflectionTemplateLib/rtl/builder/FunctorContainer.h index 73afd576..2ecfbf4c 100644 --- a/ReflectionTemplateLib/detail/inc/FunctorContainer.h +++ b/ReflectionTemplateLib/rtl/builder/FunctorContainer.h @@ -15,8 +15,8 @@ #include #include -#include "LambdaCache.h" -#include "Constants.h" +#include "lambda_cache.h" +#include "rtl_constants.h" #include "CallReflector.h" #include "SetupFunction.h" #include "SetupConstructor.h" @@ -74,27 +74,21 @@ namespace rtl { pGetIndex (lambda providing index if the functor is already registered) pUpdate (lambda updating the already registered functors/ctor/d'tor set) @return: index of newly added or already existing lambda in vector 'm_functors'. - */ static std::pair pushBack(const FunctionLambda& pFunctor, - std::function pGetIndex, - std::function pUpdate) + */ static std::size_t pushBack(const FunctionLambda& pFunctor, + std::function pGetIndex, + std::function pUpdate) { //critical section, thread safe. static std::mutex mtx; std::lock_guard lock(mtx); - auto& lamdba_store = lambda_cache::get<_signature...>(); std::size_t index = pGetIndex(); - - if (index == rtl::index_none) - { - index = lamdba_store.get().size(); - - lamdba_store.push(pFunctor); - getFunctorTable().push_back(pFunctor); - + if (index == rtl::index_none) { + index = getFunctorTable().size(); pUpdate(index); + getFunctorTable().push_back(pFunctor); } - return { index, &lamdba_store }; + return index; } //friends :) diff --git a/ReflectionTemplateLib/detail/inc/MethodContainer.h b/ReflectionTemplateLib/rtl/builder/MethodContainer.h similarity index 77% rename from ReflectionTemplateLib/detail/inc/MethodContainer.h rename to ReflectionTemplateLib/rtl/builder/MethodContainer.h index 9d8a53f8..0a84ffd6 100644 --- a/ReflectionTemplateLib/detail/inc/MethodContainer.h +++ b/ReflectionTemplateLib/rtl/builder/MethodContainer.h @@ -15,7 +15,7 @@ #include #include -#include "Constants.h" +#include "rtl_constants.h" #include "CallReflector.h" #include "SetupMethod.h" @@ -44,8 +44,6 @@ namespace rtl { public: - using lambda_t = detail::lambda_registry; - //every MethodContainer will have a unique-id. static std::size_t getContainerId() { //holds unique-id @@ -78,31 +76,24 @@ namespace rtl { /* @method: pushBack @params: pFunctor (lambda containing non-const-member-function functor call) - pGetIndex (lambda providing index if the functor is already registered) + pGetIndex (lambda providing lambdaIndex if the functor is already registered) pUpdate (lambda updating the already registered functors set) - @return: index of newly added or already existing lambda in vector 'm_methodPtrs'. - */ static std::pair pushBack(const MethodLambda& pFunctor, - std::function pGetIndex, - std::function pUpdateIndex) + @return: lambdaIndex of newly added or already existing lambda in vector 'm_methodPtrs'. + */ static std::size_t pushBack(const MethodLambda& pFunctor, + std::function pGetIndex, + std::function pUpdateIndex) { //critical section, thread safe. static std::mutex mtx; std::lock_guard lock(mtx); std::size_t index = pGetIndex(); - auto& lamdba_store = lambda_cache::get<_signature...>(); - - if (index == rtl::index_none) - { - index = lamdba_store.get().size(); - - lamdba_store.push(pFunctor); - - getFunctorTable().push_back(pFunctor); - + if (index == rtl::index_none) { + index = getFunctorTable().size(); pUpdateIndex(index); + getFunctorTable().push_back(pFunctor); } - return { index, &lamdba_store }; + return index; } //friends :) @@ -126,8 +117,6 @@ namespace rtl { public: - using lambda_t = detail::lambda_registry; - //every MethodContainer will have a unique-id. FORCE_INLINE static std::size_t getContainerId() { //holds unique-id @@ -160,31 +149,24 @@ namespace rtl { /* @method: pushBack @params: pFunctor (lambda containing const-member-function functor call) - pGetIndex (lambda providing index if the functor is already registered) + pGetIndex (lambda providing lambdaIndex if the functor is already registered) pUpdate (lambda updating the already registered functors set) - @return: index of newly added or already existing lambda in vector 'm_methodPtrs'. - */ static std::pair pushBack(const MethodLambda& pFunctor, - std::function pGetIndex, - std::function pUpdateIndex) + @return: lambdaIndex of newly added or already existing lambda in vector 'm_methodPtrs'. + */ static std::size_t pushBack(const MethodLambda& pFunctor, + std::function pGetIndex, + std::function pUpdateIndex) { //critical section, thread safe. static std::mutex mtx; std::lock_guard lock(mtx); - auto& lamdba_store = lambda_cache::get<_signature...>(); std::size_t index = pGetIndex(); - - if (index == rtl::index_none) - { - index = lamdba_store.get().size(); - - lamdba_store.push(pFunctor); - - getFunctorTable().push_back(pFunctor); - + if (index == rtl::index_none) { + index = getFunctorTable().size(); pUpdateIndex(index); + getFunctorTable().push_back(pFunctor); } - return { index, &lamdba_store }; + return index; } //friends :) diff --git a/ReflectionTemplateLib/detail/inc/RObjectBuilder.h b/ReflectionTemplateLib/rtl/builder/RObjectBuilder.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/RObjectBuilder.h rename to ReflectionTemplateLib/rtl/builder/RObjectBuilder.h diff --git a/ReflectionTemplateLib/detail/inc/RObjectBuilder.hpp b/ReflectionTemplateLib/rtl/builder/RObjectBuilder.hpp similarity index 100% rename from ReflectionTemplateLib/detail/inc/RObjectBuilder.hpp rename to ReflectionTemplateLib/rtl/builder/RObjectBuilder.hpp diff --git a/ReflectionTemplateLib/builder/inc/RecordBuilder.h b/ReflectionTemplateLib/rtl/builder/RecordBuilder.h similarity index 100% rename from ReflectionTemplateLib/builder/inc/RecordBuilder.h rename to ReflectionTemplateLib/rtl/builder/RecordBuilder.h diff --git a/ReflectionTemplateLib/builder/inc/RecordBuilder.hpp b/ReflectionTemplateLib/rtl/builder/RecordBuilder.hpp similarity index 100% rename from ReflectionTemplateLib/builder/inc/RecordBuilder.hpp rename to ReflectionTemplateLib/rtl/builder/RecordBuilder.hpp diff --git a/ReflectionTemplateLib/builder/inc/Reflect.h b/ReflectionTemplateLib/rtl/builder/Reflect.h similarity index 99% rename from ReflectionTemplateLib/builder/inc/Reflect.h rename to ReflectionTemplateLib/rtl/builder/Reflect.h index e187d34b..3d7f37e8 100644 --- a/ReflectionTemplateLib/builder/inc/Reflect.h +++ b/ReflectionTemplateLib/rtl/builder/Reflect.h @@ -12,7 +12,7 @@ #pragma once #include -#include "Constants.h" +#include "rtl_constants.h" #include "Builder.h" namespace rtl::builder diff --git a/ReflectionTemplateLib/builder/inc/Reflect.hpp b/ReflectionTemplateLib/rtl/builder/Reflect.hpp similarity index 100% rename from ReflectionTemplateLib/builder/inc/Reflect.hpp rename to ReflectionTemplateLib/rtl/builder/Reflect.hpp diff --git a/ReflectionTemplateLib/detail/inc/ReflectionBuilder.h b/ReflectionTemplateLib/rtl/builder/ReflectionBuilder.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/ReflectionBuilder.h rename to ReflectionTemplateLib/rtl/builder/ReflectionBuilder.h diff --git a/ReflectionTemplateLib/detail/inc/ReflectionBuilder.hpp b/ReflectionTemplateLib/rtl/builder/ReflectionBuilder.hpp similarity index 100% rename from ReflectionTemplateLib/detail/inc/ReflectionBuilder.hpp rename to ReflectionTemplateLib/rtl/builder/ReflectionBuilder.hpp diff --git a/ReflectionTemplateLib/detail/inc/SetupConstructor.h b/ReflectionTemplateLib/rtl/builder/SetupConstructor.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/SetupConstructor.h rename to ReflectionTemplateLib/rtl/builder/SetupConstructor.h diff --git a/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp b/ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp similarity index 87% rename from ReflectionTemplateLib/detail/inc/SetupConstructor.hpp rename to ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp index e3ca1fb5..a090b24f 100644 --- a/ReflectionTemplateLib/detail/inc/SetupConstructor.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp @@ -25,9 +25,6 @@ namespace rtl::detail { return [](const FunctorId& pFunctorId, alloc pAllocType, const FunctorId& pClonerId, _signature&&...params)-> Return { - std::size_t signatureId = TypeId...>>::get(); - assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); - if constexpr (sizeof...(_signature) == 0 && !std::is_default_constructible_v<_recordType>) { //default constructor, private or deleted. return { error::TypeNotDefaultConstructible, RObject{} }; @@ -75,9 +72,6 @@ namespace rtl::detail { return [](const FunctorId& pFunctorId, const RObject& pOther, alloc pAllocOn) -> Return { - std::size_t signatureId = TypeId>::get(); - assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); - const auto& srcObj = pOther.view<_recordType>()->get(); switch (pAllocOn) { @@ -103,9 +97,6 @@ namespace rtl::detail { return [](const FunctorId& pFunctorId, const RObject& pOther, alloc pAllocOn) -> Return { - std::size_t signatureId = TypeId>::get(); - assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); - return { error::TypeNotCopyConstructible, RObject{} @@ -146,18 +137,23 @@ namespace rtl::detail return (itr != ctorSet.end() ? itr->second : index_none); }; + //auto& lambdaCache = lambda_cache::get<_signature...>(); + //const auto& pushLambdaHopper = [&]()-> std::size_t + //{ + // return lambdaCache.push_ctor<_recordType>(); + //}; + //add the lambda in 'FunctorContainer'. - auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); + auto lambdaIndex = _derivedType::pushBack(getConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); return detail::FunctorId { lambdaIndex, - rtl::index_none, returnId, recordId, containerId, _derivedType::template getSignatureStr<_recordType>(true), - lambdaPtr + nullptr//&lambdaCache }; } @@ -185,18 +181,22 @@ namespace rtl::detail return (itr != ctorSet.end() ? itr->second : index_none); }; - //add the lambda in 'FunctorContainer'. - auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getCopyConstructorCaller<_recordType>(), getIndex, updateIndex); + //auto& lambdaCache = lambda_cache::get<_signature...>(); + //const auto& pushLambdaHopper = [&]()-> std::size_t + //{ + // return lambdaCache.push_cloner<_recordType>(); + //}; + //add the lambda in 'FunctorContainer'. + auto lambdaIndex = _derivedType::pushBack(getCopyConstructorCaller<_recordType>(), getIndex, updateIndex); return detail::FunctorId { lambdaIndex, - rtl::index_none, returnId, recordId, containerId, _derivedType::template getSignatureStr<_recordType>(true), - lambdaPtr + nullptr//&lambdaCache }; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/SetupFunction.h b/ReflectionTemplateLib/rtl/builder/SetupFunction.h similarity index 97% rename from ReflectionTemplateLib/detail/inc/SetupFunction.h rename to ReflectionTemplateLib/rtl/builder/SetupFunction.h index d8ef3a24..bdcad635 100644 --- a/ReflectionTemplateLib/detail/inc/SetupFunction.h +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.h @@ -11,8 +11,7 @@ #pragma once -#include "FunctorId.h" -#include "FunctorRegistry.h" +#include "forward_decls.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/detail/inc/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp similarity index 83% rename from ReflectionTemplateLib/detail/inc/SetupFunction.hpp rename to ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index 9390ee3b..c3a80b2d 100644 --- a/ReflectionTemplateLib/detail/inc/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -13,7 +13,8 @@ #include -#include "FunctorCache.h" +#include "lambda_cache.h" +#include "functor_cache.h" #include "SetupFunction.h" #include "RObjectBuilder.hpp" @@ -28,9 +29,6 @@ namespace rtl { return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { - std::size_t signatureId = TypeId...>>::get(); - assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); - pFunctor(std::forward<_signature>(params)...); return { error::None, RObject{} }; }; @@ -48,9 +46,6 @@ namespace rtl { constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); - std::size_t signatureId = TypeId...>>::get(); - assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); - if constexpr (std::is_reference_v<_returnType>) { /* if the function returns reference, this block will be retained by compiler. Note: reference to temporary or dangling is not checked here. @@ -87,39 +82,42 @@ namespace rtl template inline const detail::FunctorId SetupFunction<_derivedType>::addFunctor(_returnType(*pFunctor)(_signature...), std::size_t pRecordId) { - auto& functorCache = functor_cache::get<_returnType, _signature...>(); - std::size_t functorIndex = rtl::index_none; + auto& functorCache = functor_cache<_returnType, _signature...>::get(); // called from '_derivedType' ('FunctorContainer') const auto& updateIndex = [&](std::size_t pIndex)-> void { - functorIndex = functorCache.get().size(); + //functorIndex = functorCache.get().size(); functorCache.push(pFunctor, pIndex); }; // called from '_derivedType' ('FunctorContainer') const auto& getIndex = [&]()-> std::size_t { - auto [functor_i, lambda_i] = functorCache.find(pFunctor); - functorIndex = functor_i; - return lambda_i; + std::size_t lambda_index = functorCache.find(pFunctor); + return lambda_index; }; + //auto& lambdaCache = lambda_cache::get<_signature...>(); + //const auto& pushLambdaHopper = [&]()-> std::size_t + //{ + // return lambdaCache.push_function<_returnType>(); + //}; + //generate a type-id of '_returnType'. const std::size_t returnId = TypeId>::get(); //finally add the lambda 'functor' in 'FunctorContainer' lambda vector and get the index. - auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getCaller(pFunctor), getIndex, updateIndex); + auto lambdaIndex = _derivedType::pushBack(getCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. return detail::FunctorId { lambdaIndex, - functorIndex, returnId, pRecordId, _derivedType::getContainerId(), _derivedType::template getSignatureStr<_returnType>(), - lambdaPtr + nullptr//&lambdaCache }; } } diff --git a/ReflectionTemplateLib/detail/inc/SetupMethod.h b/ReflectionTemplateLib/rtl/builder/SetupMethod.h similarity index 98% rename from ReflectionTemplateLib/detail/inc/SetupMethod.h rename to ReflectionTemplateLib/rtl/builder/SetupMethod.h index 1e08fc9e..768bcff4 100644 --- a/ReflectionTemplateLib/detail/inc/SetupMethod.h +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.h @@ -11,8 +11,7 @@ #pragma once -#include "FunctorId.h" -#include "FunctorRegistry.h" +#include "forward_decls.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/detail/inc/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp similarity index 81% rename from ReflectionTemplateLib/detail/inc/SetupMethod.hpp rename to ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 90f6d9bb..8b791d0b 100644 --- a/ReflectionTemplateLib/detail/inc/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -14,10 +14,11 @@ #include #include "view.h" -#include "TypeId.h" +#include "rtl_typeid.h" #include "SetupMethod.h" #include "RObjectBuilder.hpp" -#include "FunctorCache.h" +#include "functor_cache_const.h" +#include "functor_cache_nonconst.h" namespace rtl::detail { @@ -30,15 +31,6 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - std::size_t signatureId = TypeId...>>::get(); - assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); - - //using lambda_t = lambda_registry...>; - - //lambda_t registry = static_cast(pFunctorId.m_lambda); - - //registry-> - if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; } @@ -59,9 +51,6 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - std::size_t signatureId = TypeId...>>::get(); - assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); - if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; } @@ -103,9 +92,6 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - std::size_t signatureId = TypeId...>>::get(); - assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); - const _recordType& target = pTargetObj.view<_recordType>()->get(); (target.*pFunctor)(std::forward<_signature>(params)...); return { error::None, RObject{} }; @@ -122,9 +108,6 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - std::size_t signatureId = TypeId...>>::get(); - assert((pFunctorId.m_lambda->m_signatureId == signatureId) && "Type resolution system failed!"); - constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); //'target' is const and 'pFunctor' is const-member-function. const _recordType& target = pTargetObj.view<_recordType>()->get(); @@ -165,56 +148,59 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...)) { - auto& functorCache = functor_cache::get<_recordType, _returnType, _signature...>(); - std::size_t functorIndex = rtl::index_none; + auto& functorCache = functor_cache_nonconst<_recordType, _returnType, _signature...>::get(); // called from '_derivedType' (MethodContainer) const auto& updateIndex = [&](std::size_t pIndex)->void { - functorIndex = functorCache.get().size(); functorCache.push(pFunctor, pIndex); }; // called from '_derivedType' (MethodContainer) const auto& getIndex = [&]()-> std::size_t { - auto [functor_i, lambda_i] = functorCache.find(pFunctor); - functorIndex = functor_i; - return lambda_i; + std::size_t lambdaIndex = functorCache.find(pFunctor); + return lambdaIndex; }; + //auto& lambdaCache = lambda_cache::get<_signature...>(); + //const auto& pushLambdaHopper = [&]() + //{ + // std::size_t lambdaIndex = lambdaCache.get().size(); + // lambdaCache.push(); + // return lambdaIndex; + //}; + //generate a type-id of '_returnType'. const std::size_t retTypeId = TypeId>::get(); //finally add the lambda 'functor' in 'MethodContainer' lambda vector and get the index. if constexpr (std::is_same_v<_returnType, void>) { - auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto lambdaIndex = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. - return detail::FunctorId { + return detail::FunctorId{ lambdaIndex, - functorIndex, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), _derivedType::template getSignatureStr<_recordType, _returnType>(), - lambdaPtr + nullptr }; } else { - auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto lambdaIndex = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. return detail::FunctorId { lambdaIndex, - functorIndex, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), _derivedType::template getSignatureStr<_recordType, _returnType>(), - lambdaPtr + nullptr }; } } @@ -234,57 +220,62 @@ namespace rtl::detail inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const) { - auto& functorCache = functor_cache::get<_recordType, _returnType, _signature...>(); - std::size_t functorIndex = rtl::index_none; + auto& functorCache = functor_cache_const<_recordType, _returnType, _signature...>::get(); + + //std::size_t functorIndex = rtl::index_none; // called from '_derivedType' (MethodContainer) const auto& updateIndex = [&](std::size_t pIndex)-> void { - functorIndex = functorCache.get().size(); + //functorIndex = functorCache.get().size(); functorCache.push(pFunctor, pIndex); }; // called from '_derivedType' (MethodContainer) const auto& getIndex = [&]()-> std::size_t { - auto [functor_i, lambda_i] = functorCache.find(pFunctor); - functorIndex = functor_i; - return lambda_i; + std::size_t lambdaIndex = functorCache.find(pFunctor); + return lambdaIndex; }; + //auto& lambdaCache = lambda_cache::get<_signature...>(); + //const auto& pushLambdaHopper = [&]() { + // std::size_t lambdaIndex = lambdaCache.get().size(); + // lambdaCache.push(); + // return lambdaIndex; + //}; + //generate a type-id of '_returnType'. const std::size_t retTypeId = TypeId>::get(); //finally add the lambda 'functor' in 'MethodContainer' lambda vector and get the index. if constexpr (std::is_same_v<_returnType, void>) { - auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto lambdaIndex = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. return detail::FunctorId { - lambdaIndex, - functorIndex, + lambdaIndex, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), _derivedType::template getSignatureStr<_recordType, _returnType>(), - lambdaPtr + nullptr//&lambdaCache }; } else { - auto [lambdaIndex, lambdaPtr] = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); + auto lambdaIndex = _derivedType::pushBack(getMethodCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. - return detail::FunctorId { + return detail::FunctorId{ lambdaIndex, - functorIndex, retTypeId, TypeId<_recordType>::get(), _derivedType::getContainerId(), _derivedType::template getSignatureStr<_recordType, _returnType>(), - lambdaPtr + nullptr// &lambdaCache }; } } diff --git a/ReflectionTemplateLib/rtl/cache/CMakeLists.txt b/ReflectionTemplateLib/rtl/cache/CMakeLists.txt new file mode 100644 index 00000000..bd77a74f --- /dev/null +++ b/ReflectionTemplateLib/rtl/cache/CMakeLists.txt @@ -0,0 +1,12 @@ +# ReflectionTemplateLibrary-CPP/ReflectionTemplateLib/cache/CMakeLists.txt + +# Collect headers (absolute paths) +set(LOCAL_HEADERS + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_cache.h" + "${CMAKE_CURRENT_SOURCE_DIR}/functor_cache.h" + "${CMAKE_CURRENT_SOURCE_DIR}/functor_cache_const.h" + "${CMAKE_CURRENT_SOURCE_DIR}/functor_cache_nonconst.h" +) + +target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) +source_group("Header Files\\Cache" FILES ${LOCAL_HEADERS}) \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache.h b/ReflectionTemplateLib/rtl/cache/functor_cache.h new file mode 100644 index 00000000..32ef06d1 --- /dev/null +++ b/ReflectionTemplateLib/rtl/cache/functor_cache.h @@ -0,0 +1,61 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "functor.h" + +namespace rtl::detail +{ + template + struct functor_cache + { + using fptr_t = return_t(*)(signature_ts...); + using functor_t = dispatch::functor; + + static functor_cache& get() + { + static functor_cache instance; + return instance; + } + + const dispatch::functor_hop* push(const functor_t& functor, std::size_t lambda_index) + { + m_cache.emplace_back(std::make_pair(functor, lambda_index)); + return &(m_cache.back().first); + } + + std::size_t find(fptr_t fptr) + { + for (auto& itr : m_cache) + { + const auto& functor = itr.first; + if (fptr == functor.get()) { + return itr.second; + } + } + return rtl::index_none; + } + + functor_cache(functor_cache&&) = delete; + functor_cache(const functor_cache&) = delete; + functor_cache& operator=(functor_cache&&) = delete; + functor_cache& operator=(const functor_cache&) = delete; + + private: + + // No reallocation occurs; original objects stay intact + std::deque> m_cache; + functor_cache() {} + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_const.h b/ReflectionTemplateLib/rtl/cache/functor_cache_const.h new file mode 100644 index 00000000..534d30cf --- /dev/null +++ b/ReflectionTemplateLib/rtl/cache/functor_cache_const.h @@ -0,0 +1,61 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "functor_const.h" + +namespace rtl::detail +{ + template + struct functor_cache_const + { + using fptr_t = return_t(record_t::*)(signature_ts...) const; + using functor_t = dispatch::functor_const; + + static functor_cache_const& get() + { + static functor_cache_const instance; + return instance; + } + + const dispatch::functor_hop* push(const functor_t& functor, std::size_t lambda_index) + { + m_cache.emplace_back(std::make_pair(functor, lambda_index)); + return &(m_cache.back().first); + } + + std::size_t find(fptr_t fptr) + { + for (auto& itr : m_cache) + { + const auto& functor = itr.first; + if (fptr == functor.get()) { + return itr.second; + } + } + return rtl::index_none; + } + + functor_cache_const(functor_cache_const&&) = delete; + functor_cache_const(const functor_cache_const&) = delete; + functor_cache_const& operator=(functor_cache_const&&) = delete; + functor_cache_const& operator=(const functor_cache_const&) = delete; + + private: + + // No reallocation occurs; original objects stay intact + std::deque> m_cache; + functor_cache_const() {} + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h b/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h new file mode 100644 index 00000000..3b9ba13d --- /dev/null +++ b/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h @@ -0,0 +1,61 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "functor_nonconst.h" + +namespace rtl::detail +{ + template + struct functor_cache_nonconst + { + using fptr_t = return_t(record_t::*)(signature_ts...); + using functor_t = typename dispatch::functor_nonconst; + + static functor_cache_nonconst& get() + { + static functor_cache_nonconst instance; + return instance; + } + + const dispatch::functor_hop* push(const functor_t& functor, std::size_t lambda_index) + { + m_cache.emplace_back(std::make_pair(functor, lambda_index)); + return &(m_cache.back().first); + } + + std::size_t find(fptr_t fptr) + { + for (auto& itr : m_cache) + { + const auto& functor = itr.first; + if (fptr == functor.get()) { + return itr.second; + } + } + return rtl::index_none; + } + + functor_cache_nonconst(functor_cache_nonconst&&) = delete; + functor_cache_nonconst(const functor_cache_nonconst&) = delete; + functor_cache_nonconst& operator=(functor_cache_nonconst&&) = delete; + functor_cache_nonconst& operator=(const functor_cache_nonconst&) = delete; + + private: + + // No reallocation occurs; original objects stay intact + std::deque> m_cache; + functor_cache_nonconst() {} + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/lambda_cache.h b/ReflectionTemplateLib/rtl/cache/lambda_cache.h new file mode 100644 index 00000000..4a37b970 --- /dev/null +++ b/ReflectionTemplateLib/rtl/cache/lambda_cache.h @@ -0,0 +1,45 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "lambda.h" + +namespace rtl::detail +{ + template + struct lambda_cache + { + static lambda_cache& get() { + static lambda_cache instance; + return instance; + } + + std::pair push(const dispatch::lambda& lambda_hop) + { + m_cache.push_back(lambda_hop); + return { (m_cache.size() - 1), &m_cache.back() }; + } + + lambda_cache(lambda_cache&&) = delete; + lambda_cache(const lambda_cache&) = delete; + lambda_cache& operator=(lambda_cache&&) = delete; + lambda_cache& operator=(const lambda_cache&) = delete; + + private: + + // No reallocation occurs; original objects stay intact + std::deque> m_cache; + lambda_cache() {} + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/CMakeLists.txt b/ReflectionTemplateLib/rtl/detail/CMakeLists.txt new file mode 100644 index 00000000..c99483ce --- /dev/null +++ b/ReflectionTemplateLib/rtl/detail/CMakeLists.txt @@ -0,0 +1,10 @@ +# ReflectionTemplateLibrary-CPP/ReflectionTemplateLib/detail/CMakeLists.txt + +# Make the 'inc' folder visible as a public include dir +target_include_directories(ReflectionTemplateLib + PUBLIC + "${CMAKE_CURRENT_SOURCE_DIR}/inc" +) + +add_subdirectory(inc) +add_subdirectory(src) \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt b/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt new file mode 100644 index 00000000..343cfb2f --- /dev/null +++ b/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt @@ -0,0 +1,18 @@ +# ReflectionTemplateLibrary-CPP/ReflectionTemplateLib/detail/inc/CMakeLists.txt + +# All headers in this folder (absolute paths) +set(LOCAL_HEADERS + "${CMAKE_CURRENT_SOURCE_DIR}/ConversionUtils.h" + "${CMAKE_CURRENT_SOURCE_DIR}/CxxReflection.h" + "${CMAKE_CURRENT_SOURCE_DIR}/forward_decls.h" + "${CMAKE_CURRENT_SOURCE_DIR}/FunctorId.h" + "${CMAKE_CURRENT_SOURCE_DIR}/ReflectCast.h" + "${CMAKE_CURRENT_SOURCE_DIR}/ReflectCast.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/ReflectCastUtil.h" + "${CMAKE_CURRENT_SOURCE_DIR}/RObjectId.h" + "${CMAKE_CURRENT_SOURCE_DIR}/RObjectUPtr.h" + "${CMAKE_CURRENT_SOURCE_DIR}/RObjExtracter.h" +) + +target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) +source_group("Header Files\\Detail" FILES ${LOCAL_HEADERS}) \ No newline at end of file diff --git a/ReflectionTemplateLib/common/ConversionUtils.h b/ReflectionTemplateLib/rtl/detail/inc/ConversionUtils.h similarity index 100% rename from ReflectionTemplateLib/common/ConversionUtils.h rename to ReflectionTemplateLib/rtl/detail/inc/ConversionUtils.h diff --git a/ReflectionTemplateLib/detail/inc/CxxReflection.h b/ReflectionTemplateLib/rtl/detail/inc/CxxReflection.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/CxxReflection.h rename to ReflectionTemplateLib/rtl/detail/inc/CxxReflection.h diff --git a/ReflectionTemplateLib/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h similarity index 93% rename from ReflectionTemplateLib/detail/inc/FunctorId.h rename to ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index de0f7a89..501c083a 100644 --- a/ReflectionTemplateLib/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -11,13 +11,12 @@ #pragma once -#include "TypeId.h" -#include "Constants.h" +#include "rtl_typeid.h" +#include "rtl_constants.h" +#include "forward_decls.h" namespace rtl::detail { - class lambda_hop; - /* @class: FunctorId * 'FunctorId' object is generated for every functor (member/non-member function pointer) registered. * acts as a hash-key to lookup a particular functor in the functor-table. @@ -30,8 +29,6 @@ namespace rtl::detail //index of the functor in the functor-table. std::size_t m_lambdaIndex; - std::size_t m_functorIndex; - //return type-id of the functor registered. std::size_t m_returnId; @@ -47,7 +44,6 @@ namespace rtl::detail lambda_hop* m_lambda = nullptr; GETTER(std::size_t, LambdaIndex, m_lambdaIndex) - GETTER(std::size_t, FunctorIndex, m_functorIndex) GETTER(std::size_t, ReturnId, m_returnId); GETTER(std::size_t, RecordId, m_recordId); GETTER(std::size_t, SignatureId, m_containerId) @@ -77,7 +73,6 @@ namespace rtl::detail m_recordId == pOther.m_recordId && m_containerId == pOther.m_containerId && m_lambdaIndex == pOther.m_lambdaIndex && - m_functorIndex == pOther.m_functorIndex && m_signature == pOther.m_signature); } }; diff --git a/ReflectionTemplateLib/detail/inc/RObjExtracter.h b/ReflectionTemplateLib/rtl/detail/inc/RObjExtracter.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/RObjExtracter.h rename to ReflectionTemplateLib/rtl/detail/inc/RObjExtracter.h diff --git a/ReflectionTemplateLib/detail/inc/RObjectId.h b/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/RObjectId.h rename to ReflectionTemplateLib/rtl/detail/inc/RObjectId.h diff --git a/ReflectionTemplateLib/detail/inc/RObjectUPtr.h b/ReflectionTemplateLib/rtl/detail/inc/RObjectUPtr.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/RObjectUPtr.h rename to ReflectionTemplateLib/rtl/detail/inc/RObjectUPtr.h diff --git a/ReflectionTemplateLib/detail/inc/ReflectCast.h b/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/ReflectCast.h rename to ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h diff --git a/ReflectionTemplateLib/detail/inc/ReflectCast.hpp b/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.hpp similarity index 99% rename from ReflectionTemplateLib/detail/inc/ReflectCast.hpp rename to ReflectionTemplateLib/rtl/detail/inc/ReflectCast.hpp index 85b405aa..78e32745 100644 --- a/ReflectionTemplateLib/detail/inc/ReflectCast.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.hpp @@ -11,7 +11,7 @@ #pragma once -#include "TypeId.h" +#include "rtl_typeid.h" #include "ReflectCast.h" #include "ConversionUtils.h" diff --git a/ReflectionTemplateLib/detail/inc/ReflectCastUtil.h b/ReflectionTemplateLib/rtl/detail/inc/ReflectCastUtil.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/ReflectCastUtil.h rename to ReflectionTemplateLib/rtl/detail/inc/ReflectCastUtil.h diff --git a/ReflectionTemplateLib/common/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h similarity index 91% rename from ReflectionTemplateLib/common/forward_decls.h rename to ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index cf60c39a..1370c224 100644 --- a/ReflectionTemplateLib/common/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -11,6 +11,8 @@ #pragma once +#include "rtl_constants.h" + namespace rtl { struct Return; @@ -19,6 +21,10 @@ namespace rtl namespace detail { + struct lambda_hop; + + struct functor_hop; + struct FunctorId; template diff --git a/ReflectionTemplateLib/rtl/detail/src/CMakeLists.txt b/ReflectionTemplateLib/rtl/detail/src/CMakeLists.txt new file mode 100644 index 00000000..668c6728 --- /dev/null +++ b/ReflectionTemplateLib/rtl/detail/src/CMakeLists.txt @@ -0,0 +1,11 @@ +# ReflectionTemplateLibrary-CPP/ReflectionTemplateLib/detail/src/CMakeLists.txt + +# All .cpp files in this folder (absolute paths) +set(LOCAL_SOURCES + "${CMAKE_CURRENT_SOURCE_DIR}/CxxReflection.cpp" + "${CMAKE_CURRENT_SOURCE_DIR}/ReflectCast.cpp" + "${CMAKE_CURRENT_SOURCE_DIR}/RObjectConverters_string.cpp" +) + +target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_SOURCES}) +source_group("Source Files\\Detail" FILES ${LOCAL_SOURCES}) \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/src/CxxReflection.cpp b/ReflectionTemplateLib/rtl/detail/src/CxxReflection.cpp similarity index 99% rename from ReflectionTemplateLib/detail/src/CxxReflection.cpp rename to ReflectionTemplateLib/rtl/detail/src/CxxReflection.cpp index 762974c7..cfc2683c 100644 --- a/ReflectionTemplateLib/detail/src/CxxReflection.cpp +++ b/ReflectionTemplateLib/rtl/detail/src/CxxReflection.cpp @@ -12,7 +12,7 @@ #include #include -#include "TypeId.h" +#include "rtl_typeid.h" #include "Record.h" #include "Method.h" #include "CxxReflection.h" diff --git a/ReflectionTemplateLib/detail/src/RObjectConverters_string.cpp b/ReflectionTemplateLib/rtl/detail/src/RObjectConverters_string.cpp similarity index 99% rename from ReflectionTemplateLib/detail/src/RObjectConverters_string.cpp rename to ReflectionTemplateLib/rtl/detail/src/RObjectConverters_string.cpp index 8e8363a3..67355763 100644 --- a/ReflectionTemplateLib/detail/src/RObjectConverters_string.cpp +++ b/ReflectionTemplateLib/rtl/detail/src/RObjectConverters_string.cpp @@ -9,7 +9,7 @@ *************************************************************************/ -#include "TypeId.h" +#include "rtl_typeid.h" #include "ReflectCast.hpp" #include diff --git a/ReflectionTemplateLib/detail/src/ReflectCast.cpp b/ReflectionTemplateLib/rtl/detail/src/ReflectCast.cpp similarity index 100% rename from ReflectionTemplateLib/detail/src/ReflectCast.cpp rename to ReflectionTemplateLib/rtl/detail/src/ReflectCast.cpp diff --git a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt new file mode 100644 index 00000000..6fa05029 --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt @@ -0,0 +1,27 @@ +# ReflectionTemplateLibrary-CPP/ReflectionTemplateLib/dispatch/CMakeLists.txt + +# Collect headers in this folder (absolute paths) +set(LOCAL_HEADERS + + "${CMAKE_CURRENT_SOURCE_DIR}/dispatch_interface.h" + "${CMAKE_CURRENT_SOURCE_DIR}/functor.h" + "${CMAKE_CURRENT_SOURCE_DIR}/functor_const.h" + "${CMAKE_CURRENT_SOURCE_DIR}/functor_nonconst.h" + + "${CMAKE_CURRENT_SOURCE_DIR}/lambda.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_ctor.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_copy_ctor.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method_const.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method_nonconst.hpp" + + "${CMAKE_CURRENT_SOURCE_DIR}/CallReflector.h" + "${CMAKE_CURRENT_SOURCE_DIR}/FunctionCaller.h" + "${CMAKE_CURRENT_SOURCE_DIR}/FunctionCaller.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/MethodInvoker.h" + "${CMAKE_CURRENT_SOURCE_DIR}/MethodInvoker.hpp" + +) + +target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) +source_group("Header Files\\Dispatch" FILES ${LOCAL_HEADERS}) \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/CallReflector.h b/ReflectionTemplateLib/rtl/dispatch/CallReflector.h similarity index 99% rename from ReflectionTemplateLib/detail/inc/CallReflector.h rename to ReflectionTemplateLib/rtl/dispatch/CallReflector.h index 20ad94a4..4940eb8f 100644 --- a/ReflectionTemplateLib/detail/inc/CallReflector.h +++ b/ReflectionTemplateLib/rtl/dispatch/CallReflector.h @@ -13,7 +13,7 @@ #include #include "RObject.h" -#include "Constants.h" +#include "rtl_constants.h" #include "FunctorId.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/detail/inc/FunctionCaller.h b/ReflectionTemplateLib/rtl/dispatch/FunctionCaller.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/FunctionCaller.h rename to ReflectionTemplateLib/rtl/dispatch/FunctionCaller.h diff --git a/ReflectionTemplateLib/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/dispatch/FunctionCaller.hpp similarity index 100% rename from ReflectionTemplateLib/detail/inc/FunctionCaller.hpp rename to ReflectionTemplateLib/rtl/dispatch/FunctionCaller.hpp diff --git a/ReflectionTemplateLib/detail/inc/MethodInvoker.h b/ReflectionTemplateLib/rtl/dispatch/MethodInvoker.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/MethodInvoker.h rename to ReflectionTemplateLib/rtl/dispatch/MethodInvoker.h diff --git a/ReflectionTemplateLib/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/dispatch/MethodInvoker.hpp similarity index 100% rename from ReflectionTemplateLib/detail/inc/MethodInvoker.hpp rename to ReflectionTemplateLib/rtl/dispatch/MethodInvoker.hpp diff --git a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h b/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h new file mode 100644 index 00000000..a9eeae00 --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h @@ -0,0 +1,80 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "rtl_typeid.h" +#include "rtl_constants.h" + +namespace rtl::dispatch +{ + struct functor_hop; + + template + struct lambda; + + struct lambda_hop + { + const functor_hop* m_functor = nullptr; + + std::vector m_argsTypeIds; + std::size_t m_signatureId = detail::TypeId<>::None; + + template + const lambda& get() const + { + return (*static_cast*>(this)); + } + }; +} + + +namespace rtl::dispatch +{ + template + struct functor; + + template + struct functor_const; + + template + struct functor_nonconst; + + struct functor_hop + { + const lambda_hop* m_lambda = nullptr; + + std::size_t m_recordId = detail::TypeId<>::None; + std::size_t m_returnId = detail::TypeId<>::None; + std::size_t m_signatureId = detail::TypeId<>::None; + detail::methodQ m_qualifier = detail::methodQ::None; + + template + const functor& get() const + { + return *(static_cast*>(this)); + } + + template + const functor_const& get_const() const + { + return *(static_cast*>(this)); + } + + template + const functor_nonconst& get_nonconst() const + { + return *(static_cast*>(this)); + } + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h new file mode 100644 index 00000000..5164719d --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -0,0 +1,43 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "dispatch_interface.h" + +namespace rtl::dispatch +{ + template + struct functor: public functor_hop + { + using fptr_t = return_t(*)(signature_ts...); + + fptr_t get() const + { + return m_functor; + } + + return_t operator()(signature_ts&&...params) const + { + return (*m_functor)(std::forward(params)...); + } + + functor(fptr_t fptr) :m_functor(fptr) + { + m_returnId = detail::TypeId::get(); + m_signatureId = detail::TypeId>::get(); + } + + private: + + fptr_t m_functor; + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_const.h b/ReflectionTemplateLib/rtl/dispatch/functor_const.h new file mode 100644 index 00000000..fff2d5ff --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/functor_const.h @@ -0,0 +1,45 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "dispatch_interface.h" + +namespace rtl::dispatch +{ + template + struct functor_const : public functor_hop + { + using fptr_t = return_t(record_t::*)(signature_ts...) const; + + fptr_t get() const + { + return m_functor; + } + + return_t operator()(const record_t& pTarget, signature_ts&&...params) const + { + return (pTarget.*m_functor)(std::forward(params)...); + } + + functor_const(fptr_t fptr) :m_functor(fptr) + { + m_returnId = detail::TypeId::get(); + m_signatureId = detail::TypeId>::get(); + } + + private: + + fptr_t m_functor; + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h b/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h new file mode 100644 index 00000000..646eef67 --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h @@ -0,0 +1,45 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "dispatch_interface.h" + +namespace rtl::dispatch +{ + template + struct functor_nonconst : public functor_hop + { + using fptr_t = return_t(record_t::*)(signature_ts...); + + fptr_t get() const + { + return m_functor; + } + + return_t operator()(record_t& pTarget, signature_ts&&...params) const + { + return (pTarget.*m_functor)(std::forward(params)...); + } + + functor_nonconst(fptr_t fptr) :m_functor(fptr) + { + m_returnId = detail::TypeId::get(); + m_signatureId = detail::TypeId>::get(); + } + + private: + + fptr_t m_functor; + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h new file mode 100644 index 00000000..10a54382 --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -0,0 +1,58 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include +#include + +#include "forward_decls.h" +#include "dispatch_interface.h" + +namespace rtl::dispatch +{ + template + struct lambda: public lambda_hop + { + using lambda_t = std::function; + + template + void init_ctor() const; + + template + void init_cloner() const; + + template + void init_function() const; + + template + void init_method_const() const; + + template + void init_method_nonconst() const; + + Return operator()(signature_ts&&...params) const + { + return m_hopper(this, std::forward(params)...); + } + + private: + + lambda(const functor_hop* fptr_hopper) + { + detail::TypeId::get(m_argsTypeIds); + m_signatureId = detail::TypeId>::get(); + m_functor = fptr_hopper; + } + + lambda_t m_hopper; + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/detail/inc/LambdaBridge.h b/ReflectionTemplateLib/rtl/dispatch/lambda_copy_ctor.hpp similarity index 66% rename from ReflectionTemplateLib/detail/inc/LambdaBridge.h rename to ReflectionTemplateLib/rtl/dispatch/lambda_copy_ctor.hpp index b467bf49..dd8b664c 100644 --- a/ReflectionTemplateLib/detail/inc/LambdaBridge.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_copy_ctor.hpp @@ -11,23 +11,16 @@ #pragma once -#include "forward_decls.h" -#include "FunctorId.h" -#include "FunctorRegistry.h" +#include "lambda.h" +#include "RObjectBuilder.hpp" -namespace rtl::detail::bridge +namespace rtl::dispatch { - template - struct lambda_def - { - template - static auto get() - { - return [](const FunctorId& functorId, signature_ts&&...params)-> Return - { - return { error::None, RObject{} }; - }; - } - }; + template + template + inline void lambda::init_cloner() const + { + + } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp new file mode 100644 index 00000000..e864c2f7 --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp @@ -0,0 +1,25 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "lambda.h" +#include "RObjectBuilder.hpp" + +namespace rtl::dispatch +{ + template + template + inline void lambda::init_ctor() const + { + + } +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp new file mode 100644 index 00000000..bd980c3f --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp @@ -0,0 +1,70 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "lambda.h" +#include "RObjectBuilder.hpp" + +namespace rtl::dispatch +{ + template + template + inline void lambda::init_function() const + { + if constexpr (std::is_same_v) + { + m_hopper = [](const lambda_hop* hopper, signature_ts&&... params) -> Return + { + auto& functor = hopper->m_functor->get(); + + functor(std::forward(params)...); + + return{ error::None, RObject{} }; + }; + } + else + { + m_hopper = [](const lambda_hop* hopper, signature_ts&&...params) -> Return + { + auto& functor = hopper->m_functor->get(); + + constexpr bool isConstCastSafe = (!traits::is_const_v); + if constexpr (std::is_reference_v) + { + using T = traits::raw_t; + const T& retObj = functor(std::forward(params)...); + + return{ error::None, + builder::RObjectBuilder::template build( + &retObj, + std::nullopt, + isConstCastSafe) + }; + } + else { + + auto&& retObj = functor(std::forward(params)...); + using T = std::remove_cvref_t; + + return{ error::None, + builder::RObjectBuilder::template build( + std::forward(retObj), + std::nullopt, + isConstCastSafe) + }; + } + }; + } + } +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp new file mode 100644 index 00000000..d6c1a39e --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp @@ -0,0 +1,25 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "lambda.h" +#include "RObjectBuilder.hpp" + +namespace rtl::dispatch +{ + template + template + inline void lambda::init_method_const() const + { + + } +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp new file mode 100644 index 00000000..9203bfd7 --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp @@ -0,0 +1,24 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "lambda.h" + +namespace rtl::dispatch +{ + template + template + inline void lambda::init_method_nonconst() const + { + + } +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/CMakeLists.txt b/ReflectionTemplateLib/rtl/inc/CMakeLists.txt new file mode 100644 index 00000000..1896bc2f --- /dev/null +++ b/ReflectionTemplateLib/rtl/inc/CMakeLists.txt @@ -0,0 +1,20 @@ +# ReflectionTemplateLibrary-CPP/ReflectionTemplateLib/rtl/inc/CMakeLists.txt + +# Collect local headers (absolute paths) +set(LOCAL_HEADERS + "${CMAKE_CURRENT_SOURCE_DIR}/CxxMirror.h" + "${CMAKE_CURRENT_SOURCE_DIR}/CxxMirror.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/CxxMirrorToJson.h" + "${CMAKE_CURRENT_SOURCE_DIR}/Function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/Function.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/Method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/Method.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/Record.h" + "${CMAKE_CURRENT_SOURCE_DIR}/RObject.h" + "${CMAKE_CURRENT_SOURCE_DIR}/RObject.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/view.h" + "${CMAKE_CURRENT_SOURCE_DIR}/view.hpp" +) + +target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) +source_group("Header Files\\RTL" FILES ${LOCAL_HEADERS}) \ No newline at end of file diff --git a/ReflectionTemplateLib/access/inc/CxxMirror.h b/ReflectionTemplateLib/rtl/inc/CxxMirror.h similarity index 100% rename from ReflectionTemplateLib/access/inc/CxxMirror.h rename to ReflectionTemplateLib/rtl/inc/CxxMirror.h diff --git a/ReflectionTemplateLib/access/inc/CxxMirror.hpp b/ReflectionTemplateLib/rtl/inc/CxxMirror.hpp similarity index 100% rename from ReflectionTemplateLib/access/inc/CxxMirror.hpp rename to ReflectionTemplateLib/rtl/inc/CxxMirror.hpp diff --git a/ReflectionTemplateLib/access/inc/CxxMirrorToJson.h b/ReflectionTemplateLib/rtl/inc/CxxMirrorToJson.h similarity index 100% rename from ReflectionTemplateLib/access/inc/CxxMirrorToJson.h rename to ReflectionTemplateLib/rtl/inc/CxxMirrorToJson.h diff --git a/ReflectionTemplateLib/access/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h similarity index 99% rename from ReflectionTemplateLib/access/inc/Function.h rename to ReflectionTemplateLib/rtl/inc/Function.h index 88192f05..768ba5cf 100644 --- a/ReflectionTemplateLib/access/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -16,7 +16,7 @@ #include #include "FunctorId.h" -#include "Constants.h" +#include "rtl_constants.h" #include "FunctionCaller.h" namespace rtl { diff --git a/ReflectionTemplateLib/access/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp similarity index 100% rename from ReflectionTemplateLib/access/inc/Function.hpp rename to ReflectionTemplateLib/rtl/inc/Function.hpp diff --git a/ReflectionTemplateLib/access/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h similarity index 100% rename from ReflectionTemplateLib/access/inc/Method.h rename to ReflectionTemplateLib/rtl/inc/Method.h diff --git a/ReflectionTemplateLib/access/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp similarity index 100% rename from ReflectionTemplateLib/access/inc/Method.hpp rename to ReflectionTemplateLib/rtl/inc/Method.hpp diff --git a/ReflectionTemplateLib/access/inc/RObject.h b/ReflectionTemplateLib/rtl/inc/RObject.h similarity index 99% rename from ReflectionTemplateLib/access/inc/RObject.h rename to ReflectionTemplateLib/rtl/inc/RObject.h index 86ded7c0..58f5fc10 100644 --- a/ReflectionTemplateLib/access/inc/RObject.h +++ b/ReflectionTemplateLib/rtl/inc/RObject.h @@ -16,8 +16,9 @@ #include #include "view.h" -#include "TypeId.h" #include "RObjectId.h" + +#include "rtl_typeid.h" #include "rtl_traits.h" diff --git a/ReflectionTemplateLib/access/inc/RObject.hpp b/ReflectionTemplateLib/rtl/inc/RObject.hpp similarity index 97% rename from ReflectionTemplateLib/access/inc/RObject.hpp rename to ReflectionTemplateLib/rtl/inc/RObject.hpp index c692e8ef..51091c24 100644 --- a/ReflectionTemplateLib/access/inc/RObject.hpp +++ b/ReflectionTemplateLib/rtl/inc/RObject.hpp @@ -199,7 +199,7 @@ namespace rtl if (m_objectId.m_clonerId.has_value()) { const detail::FunctorId& functorId = m_objectId.m_clonerId.value(); - return traits::Cloner::forwardCall(functorId, *this, alloc::Heap); + return traits::Cloner::template forwardCall(functorId, *this, alloc::Heap); } return { error::CloningDisabled, RObject{} }; } @@ -211,7 +211,7 @@ namespace rtl if (m_objectId.m_clonerId.has_value()) { const detail::FunctorId& functorId = m_objectId.m_clonerId.value(); - return traits::Cloner::forwardCall(functorId, *this, alloc::Stack); + return traits::Cloner::template forwardCall(functorId, *this, alloc::Stack); } return { error::CloningDisabled, RObject{} }; } diff --git a/ReflectionTemplateLib/access/inc/Record.h b/ReflectionTemplateLib/rtl/inc/Record.h similarity index 99% rename from ReflectionTemplateLib/access/inc/Record.h rename to ReflectionTemplateLib/rtl/inc/Record.h index e081b37c..b6d9fb81 100644 --- a/ReflectionTemplateLib/access/inc/Record.h +++ b/ReflectionTemplateLib/rtl/inc/Record.h @@ -16,7 +16,7 @@ #include #include "Method.h" -#include "Constants.h" +#include "rtl_constants.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/common/view.h b/ReflectionTemplateLib/rtl/inc/view.h similarity index 100% rename from ReflectionTemplateLib/common/view.h rename to ReflectionTemplateLib/rtl/inc/view.h diff --git a/ReflectionTemplateLib/common/view.hpp b/ReflectionTemplateLib/rtl/inc/view.hpp similarity index 100% rename from ReflectionTemplateLib/common/view.hpp rename to ReflectionTemplateLib/rtl/inc/view.hpp diff --git a/ReflectionTemplateLib/common/RTLibInterface.h b/ReflectionTemplateLib/rtl/rtl.h similarity index 97% rename from ReflectionTemplateLib/common/RTLibInterface.h rename to ReflectionTemplateLib/rtl/rtl.h index 2f1cdd4d..d4185e61 100644 --- a/ReflectionTemplateLib/common/RTLibInterface.h +++ b/ReflectionTemplateLib/rtl/rtl.h @@ -87,8 +87,6 @@ /* * The root reflection container that aggregates all registrations. -* Users are expected to define a singleton CxxMirror that holds all -* records and functions: * * namespace cxx { * const rtl::CxxMirror& mirror() { diff --git a/ReflectionTemplateLib/common/Constants.h b/ReflectionTemplateLib/rtl/rtl_constants.h similarity index 99% rename from ReflectionTemplateLib/common/Constants.h rename to ReflectionTemplateLib/rtl/rtl_constants.h index d595fdc0..09e927c4 100644 --- a/ReflectionTemplateLib/common/Constants.h +++ b/ReflectionTemplateLib/rtl/rtl_constants.h @@ -11,7 +11,7 @@ #pragma once -#include "error_codes.h" +#include "rtl_errors.h" namespace rtl { diff --git a/ReflectionTemplateLib/common/error_codes.h b/ReflectionTemplateLib/rtl/rtl_errors.h similarity index 100% rename from ReflectionTemplateLib/common/error_codes.h rename to ReflectionTemplateLib/rtl/rtl_errors.h diff --git a/ReflectionTemplateLib/common/rtl_traits.h b/ReflectionTemplateLib/rtl/rtl_traits.h similarity index 99% rename from ReflectionTemplateLib/common/rtl_traits.h rename to ReflectionTemplateLib/rtl/rtl_traits.h index 257ef64a..d2ccb404 100644 --- a/ReflectionTemplateLib/common/rtl_traits.h +++ b/ReflectionTemplateLib/rtl/rtl_traits.h @@ -19,8 +19,8 @@ #include #include -#include "TypeId.h" -#include "Constants.h" +#include "rtl_typeid.h" +#include "rtl_constants.h" #include "forward_decls.h" namespace rtl diff --git a/ReflectionTemplateLib/detail/inc/TypeId.h b/ReflectionTemplateLib/rtl/rtl_typeid.h similarity index 100% rename from ReflectionTemplateLib/detail/inc/TypeId.h rename to ReflectionTemplateLib/rtl/rtl_typeid.h diff --git a/ReflectionTemplateLib/rtl/src/CMakeLists.txt b/ReflectionTemplateLib/rtl/src/CMakeLists.txt new file mode 100644 index 00000000..22a75169 --- /dev/null +++ b/ReflectionTemplateLib/rtl/src/CMakeLists.txt @@ -0,0 +1,11 @@ +# ReflectionTemplateLibrary-CPP/ReflectionTemplateLib/rtl/src/CMakeLists.txt + +# Collect local sources (absolute paths) +set(LOCAL_SOURCES + "${CMAKE_CURRENT_SOURCE_DIR}/CxxMirror.cpp" + "${CMAKE_CURRENT_SOURCE_DIR}/CxxMirrorToJson.cpp" + "${CMAKE_CURRENT_SOURCE_DIR}/Function.cpp" +) + +target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_SOURCES}) +source_group("Source Files\\RTL" FILES ${LOCAL_SOURCES}) \ No newline at end of file diff --git a/ReflectionTemplateLib/access/src/CxxMirror.cpp b/ReflectionTemplateLib/rtl/src/CxxMirror.cpp similarity index 100% rename from ReflectionTemplateLib/access/src/CxxMirror.cpp rename to ReflectionTemplateLib/rtl/src/CxxMirror.cpp diff --git a/ReflectionTemplateLib/access/src/CxxMirrorToJson.cpp b/ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp similarity index 94% rename from ReflectionTemplateLib/access/src/CxxMirrorToJson.cpp rename to ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp index 0143cd39..9905c356 100644 --- a/ReflectionTemplateLib/access/src/CxxMirrorToJson.cpp +++ b/ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp @@ -27,12 +27,6 @@ static const std::string toJson(const FunctorId& pFunctorId) std::stringstream sout; sout << "{\"containerId\": \"" << std::to_string(pFunctorId.getSignatureId()) << "\","; sout << "\"lambdaIndex\": \"" << std::to_string(pFunctorId.getLambdaIndex()) << "\","; - if (pFunctorId.getFunctorIndex() != rtl::index_none) { - sout << "\"functorIndex\": \"" << std::to_string(pFunctorId.getFunctorIndex()) << "\","; - } - else { - sout << "\"functorIndex\": \"-1\","; - } if (pFunctorId.getRecordId() != TypeId<>::None) { sout << "\"recordId\": \"" << std::to_string(pFunctorId.getRecordId()) << "\","; } diff --git a/ReflectionTemplateLib/access/src/Function.cpp b/ReflectionTemplateLib/rtl/src/Function.cpp similarity index 100% rename from ReflectionTemplateLib/access/src/Function.cpp rename to ReflectionTemplateLib/rtl/src/Function.cpp From c03af5ff3b5c454adfaea05aee25e720ce28a485 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Thu, 18 Sep 2025 02:07:02 +0530 Subject: [PATCH 07/58] new dispatch-mechanism working, in-progress. --- RTLBenchmarkApp/src/ReflectedCall.cpp | 15 ++++++- RTLBenchmarkApp/src/ReflectedCall.h | 2 + RTLBenchmarkApp/src/main.cpp | 1 + .../rtl/builder/SetupConstructor.hpp | 6 --- .../rtl/builder/SetupFunction.hpp | 45 ++++++++++++------- .../rtl/builder/SetupMethod.hpp | 22 +-------- .../rtl/cache/functor_cache.h | 17 +++---- .../rtl/cache/functor_cache_const.h | 12 ++--- .../rtl/cache/functor_cache_nonconst.h | 14 +++--- .../rtl/cache/lambda_cache.h | 18 +++++--- .../rtl/detail/inc/FunctorId.h | 2 +- .../rtl/detail/inc/forward_decls.h | 11 +++-- .../rtl/dispatch/dispatch_interface.h | 26 ++++++++--- ReflectionTemplateLib/rtl/dispatch/functor.h | 2 +- .../rtl/dispatch/functor_const.h | 2 +- .../rtl/dispatch/functor_nonconst.h | 2 +- ReflectionTemplateLib/rtl/dispatch/lambda.h | 12 ++--- .../rtl/dispatch/lambda_function.hpp | 26 +++++------ ReflectionTemplateLib/rtl/rtl_traits.h | 2 + 19 files changed, 131 insertions(+), 106 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCall.cpp b/RTLBenchmarkApp/src/ReflectedCall.cpp index 4c2bf8ac..e62e3a11 100644 --- a/RTLBenchmarkApp/src/ReflectedCall.cpp +++ b/RTLBenchmarkApp/src/ReflectedCall.cpp @@ -1,8 +1,8 @@ #include +#include #include "ReflectedCall.h" -#include #include "BenchMark.h" namespace cxx @@ -46,7 +46,7 @@ namespace static auto _test0 = []() { auto err = SendMessage(bm::g_longStr).err; - + if (err != rtl::error::None) { std::cout << "[1] error: "<< rtl::to_string(err)<<"\n"; } @@ -107,6 +107,17 @@ void ReflectedCall::get(benchmark::State& state) } } +void ReflectedCall::new_design_set(benchmark::State& state) +{ + static auto& hopper = (SendMessage.getFunctors()[0].m_lambda)->get(); + static bm::argStr_t&& argStr = bm::argStr_t(bm::g_longStr); + for (auto _ : state) { + + auto error = hopper(std::forward(argStr)).err; + benchmark::DoNotOptimize(error); + } +} + void ReflectedMethodCall::set(benchmark::State& state) { diff --git a/RTLBenchmarkApp/src/ReflectedCall.h b/RTLBenchmarkApp/src/ReflectedCall.h index 59416ca2..77b410c5 100644 --- a/RTLBenchmarkApp/src/ReflectedCall.h +++ b/RTLBenchmarkApp/src/ReflectedCall.h @@ -7,6 +7,8 @@ struct ReflectedCall static void set(benchmark::State& state); static void get(benchmark::State& state); + + static void new_design_set(benchmark::State& state); }; diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index bcefd8d1..860bba04 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -10,6 +10,7 @@ BENCHMARK(NativeCall::set); BENCHMARK(StdFuncCall::set); BENCHMARK(ReflectedCall::set); +BENCHMARK(ReflectedCall::new_design_set); BENCHMARK(StdFuncMethodCall::set); BENCHMARK(ReflectedMethodCall::set); diff --git a/ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp b/ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp index a090b24f..bfa6a1cd 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp @@ -137,12 +137,6 @@ namespace rtl::detail return (itr != ctorSet.end() ? itr->second : index_none); }; - //auto& lambdaCache = lambda_cache::get<_signature...>(); - //const auto& pushLambdaHopper = [&]()-> std::size_t - //{ - // return lambdaCache.push_ctor<_recordType>(); - //}; - //add the lambda in 'FunctorContainer'. auto lambdaIndex = _derivedType::pushBack(getConstructorCaller<_recordType, _signature...>(), getIndex, updateIndex); diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index c3a80b2d..d01be707 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -15,6 +15,8 @@ #include "lambda_cache.h" #include "functor_cache.h" +#include "lambda_function.hpp" + #include "SetupFunction.h" #include "RObjectBuilder.hpp" @@ -29,6 +31,9 @@ namespace rtl { return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { + bool isAmazing = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + assert(isAmazing && "new type-system corrupted."); + pFunctor(std::forward<_signature>(params)...); return { error::None, RObject{} }; }; @@ -44,6 +49,9 @@ namespace rtl this is stored in _derivedType's (FunctorContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, _signature&&...params)-> Return { + bool isAmazing = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + assert(isAmazing && "new type-system corrupted."); + constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); if constexpr (std::is_reference_v<_returnType>) { @@ -82,42 +90,47 @@ namespace rtl template inline const detail::FunctorId SetupFunction<_derivedType>::addFunctor(_returnType(*pFunctor)(_signature...), std::size_t pRecordId) { - auto& functorCache = functor_cache<_returnType, _signature...>::get(); + const dispatch::lambda_hop* lambdaPtr = nullptr; - // called from '_derivedType' ('FunctorContainer') const auto& updateIndex = [&](std::size_t pIndex)-> void { - //functorIndex = functorCache.get().size(); - functorCache.push(pFunctor, pIndex); + auto& functorCache = dispatch::functor_cache<_returnType, _signature...>::get(); + + const dispatch::functor_hop* functor = functorCache.push(pFunctor, pIndex); + + auto& lambdaCache = dispatch::lambda_cache<_signature...>::get(); + + auto& lambda = lambdaCache.push(functor); + + lambda.init_function<_returnType>(); + + lambdaPtr = λ }; - // called from '_derivedType' ('FunctorContainer') const auto& getIndex = [&]()-> std::size_t { - std::size_t lambda_index = functorCache.find(pFunctor); - return lambda_index; + auto& functorCache = dispatch::functor_cache<_returnType, _signature...>::get(); + auto [functor, lambdaIndex] = functorCache.find(pFunctor); + if (lambdaIndex != rtl::index_none) { + lambdaPtr = functor->m_lambda; + } + return lambdaIndex; }; - //auto& lambdaCache = lambda_cache::get<_signature...>(); - //const auto& pushLambdaHopper = [&]()-> std::size_t - //{ - // return lambdaCache.push_function<_returnType>(); - //}; - //generate a type-id of '_returnType'. const std::size_t returnId = TypeId>::get(); //finally add the lambda 'functor' in 'FunctorContainer' lambda vector and get the index. auto lambdaIndex = _derivedType::pushBack(getCaller(pFunctor), getIndex, updateIndex); //construct the hash-key 'FunctorId' and return. - return detail::FunctorId { - + return detail::FunctorId{ + lambdaIndex, returnId, pRecordId, _derivedType::getContainerId(), _derivedType::template getSignatureStr<_returnType>(), - nullptr//&lambdaCache + lambdaPtr }; } } diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 8b791d0b..6cc63e50 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -148,7 +148,7 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...)) { - auto& functorCache = functor_cache_nonconst<_recordType, _returnType, _signature...>::get(); + auto& functorCache = dispatch::functor_cache_nonconst<_recordType, _returnType, _signature...>::get(); // called from '_derivedType' (MethodContainer) const auto& updateIndex = [&](std::size_t pIndex)->void @@ -163,14 +163,6 @@ namespace rtl::detail return lambdaIndex; }; - //auto& lambdaCache = lambda_cache::get<_signature...>(); - //const auto& pushLambdaHopper = [&]() - //{ - // std::size_t lambdaIndex = lambdaCache.get().size(); - // lambdaCache.push(); - // return lambdaIndex; - //}; - //generate a type-id of '_returnType'. const std::size_t retTypeId = TypeId>::get(); //finally add the lambda 'functor' in 'MethodContainer' lambda vector and get the index. @@ -219,10 +211,7 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const) { - - auto& functorCache = functor_cache_const<_recordType, _returnType, _signature...>::get(); - - //std::size_t functorIndex = rtl::index_none; + auto& functorCache = dispatch::functor_cache_const<_recordType, _returnType, _signature...>::get(); // called from '_derivedType' (MethodContainer) const auto& updateIndex = [&](std::size_t pIndex)-> void @@ -238,13 +227,6 @@ namespace rtl::detail return lambdaIndex; }; - //auto& lambdaCache = lambda_cache::get<_signature...>(); - //const auto& pushLambdaHopper = [&]() { - // std::size_t lambdaIndex = lambdaCache.get().size(); - // lambdaCache.push(); - // return lambdaIndex; - //}; - //generate a type-id of '_returnType'. const std::size_t retTypeId = TypeId>::get(); //finally add the lambda 'functor' in 'MethodContainer' lambda vector and get the index. diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache.h b/ReflectionTemplateLib/rtl/cache/functor_cache.h index 32ef06d1..13fd39b7 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache.h +++ b/ReflectionTemplateLib/rtl/cache/functor_cache.h @@ -11,17 +11,17 @@ #pragma once -#include +#include #include "functor.h" -namespace rtl::detail +namespace rtl::dispatch { template struct functor_cache { using fptr_t = return_t(*)(signature_ts...); - using functor_t = dispatch::functor; + using functor_t = functor; static functor_cache& get() { @@ -29,22 +29,22 @@ namespace rtl::detail return instance; } - const dispatch::functor_hop* push(const functor_t& functor, std::size_t lambda_index) + const functor_hop* push(const functor_t& functor, std::size_t lambda_index) { m_cache.emplace_back(std::make_pair(functor, lambda_index)); return &(m_cache.back().first); } - std::size_t find(fptr_t fptr) + std::pair find(fptr_t fptr) { for (auto& itr : m_cache) { const auto& functor = itr.first; if (fptr == functor.get()) { - return itr.second; + return { &itr.first, itr.second }; } } - return rtl::index_none; + return { nullptr, rtl::index_none }; } functor_cache(functor_cache&&) = delete; @@ -55,7 +55,8 @@ namespace rtl::detail private: // No reallocation occurs; original objects stay intact - std::deque> m_cache; + std::list> m_cache; + functor_cache() {} }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_const.h b/ReflectionTemplateLib/rtl/cache/functor_cache_const.h index 534d30cf..7d1af246 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache_const.h +++ b/ReflectionTemplateLib/rtl/cache/functor_cache_const.h @@ -11,17 +11,17 @@ #pragma once -#include +#include #include "functor_const.h" -namespace rtl::detail +namespace rtl::dispatch { template struct functor_cache_const { using fptr_t = return_t(record_t::*)(signature_ts...) const; - using functor_t = dispatch::functor_const; + using functor_t = functor_const; static functor_cache_const& get() { @@ -29,7 +29,7 @@ namespace rtl::detail return instance; } - const dispatch::functor_hop* push(const functor_t& functor, std::size_t lambda_index) + const functor_hop* push(const functor_t& functor, std::size_t lambda_index) { m_cache.emplace_back(std::make_pair(functor, lambda_index)); return &(m_cache.back().first); @@ -47,6 +47,7 @@ namespace rtl::detail return rtl::index_none; } + functor_cache_const(functor_cache_const&&) = delete; functor_cache_const(const functor_cache_const&) = delete; functor_cache_const& operator=(functor_cache_const&&) = delete; @@ -55,7 +56,8 @@ namespace rtl::detail private: // No reallocation occurs; original objects stay intact - std::deque> m_cache; + std::list> m_cache; + functor_cache_const() {} }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h b/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h index 3b9ba13d..9c8f4b5c 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h +++ b/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h @@ -11,25 +11,25 @@ #pragma once -#include +#include #include "functor_nonconst.h" -namespace rtl::detail +namespace rtl::dispatch { template struct functor_cache_nonconst { using fptr_t = return_t(record_t::*)(signature_ts...); - using functor_t = typename dispatch::functor_nonconst; - + using functor_t = typename functor_nonconst; + static functor_cache_nonconst& get() { static functor_cache_nonconst instance; return instance; } - const dispatch::functor_hop* push(const functor_t& functor, std::size_t lambda_index) + const functor_hop* push(const functor_t& functor, std::size_t lambda_index) { m_cache.emplace_back(std::make_pair(functor, lambda_index)); return &(m_cache.back().first); @@ -47,6 +47,7 @@ namespace rtl::detail return rtl::index_none; } + functor_cache_nonconst(functor_cache_nonconst&&) = delete; functor_cache_nonconst(const functor_cache_nonconst&) = delete; functor_cache_nonconst& operator=(functor_cache_nonconst&&) = delete; @@ -55,7 +56,8 @@ namespace rtl::detail private: // No reallocation occurs; original objects stay intact - std::deque> m_cache; + std::list> m_cache; + functor_cache_nonconst() {} }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/lambda_cache.h b/ReflectionTemplateLib/rtl/cache/lambda_cache.h index 4a37b970..7c011a7e 100644 --- a/ReflectionTemplateLib/rtl/cache/lambda_cache.h +++ b/ReflectionTemplateLib/rtl/cache/lambda_cache.h @@ -11,24 +11,27 @@ #pragma once -#include +#include #include "lambda.h" -namespace rtl::detail +namespace rtl::dispatch { template struct lambda_cache { - static lambda_cache& get() { + static lambda_cache& get() + { static lambda_cache instance; return instance; } - std::pair push(const dispatch::lambda& lambda_hop) + const lambda& push(const functor_hop* fptr_hopper) { - m_cache.push_back(lambda_hop); - return { (m_cache.size() - 1), &m_cache.back() }; + m_cache.push_back(lambda(fptr_hopper)); + const lambda& lambda_hop = m_cache.back(); + fptr_hopper->set_lambda(&lambda_hop); + return lambda_hop; } lambda_cache(lambda_cache&&) = delete; @@ -39,7 +42,8 @@ namespace rtl::detail private: // No reallocation occurs; original objects stay intact - std::deque> m_cache; + std::list> m_cache; + lambda_cache() {} }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index 501c083a..788827bb 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -41,7 +41,7 @@ namespace rtl::detail //signature of functor as string. platform dependent, may not be very much readable format. std::string m_signature; - lambda_hop* m_lambda = nullptr; + const dispatch::lambda_hop* m_lambda = nullptr; GETTER(std::size_t, LambdaIndex, m_lambdaIndex) GETTER(std::size_t, ReturnId, m_returnId); diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index 1370c224..46404cb9 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -21,13 +21,16 @@ namespace rtl namespace detail { - struct lambda_hop; - - struct functor_hop; - struct FunctorId; template class FunctorContainer; } + + namespace dispatch + { + struct lambda_hop; + + struct functor_hop; + } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h b/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h index a9eeae00..7ecb6723 100644 --- a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h +++ b/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h @@ -13,6 +13,7 @@ #include +#include "rtl_traits.h" #include "rtl_typeid.h" #include "rtl_constants.h" @@ -25,15 +26,21 @@ namespace rtl::dispatch struct lambda_hop { + std::size_t m_signatureId = detail::TypeId<>::None; + + traits::args_t m_argumentsId = {}; + const functor_hop* m_functor = nullptr; - std::vector m_argsTypeIds; - std::size_t m_signatureId = detail::TypeId<>::None; + const functor_hop& functor() const + { + return *m_functor; + } template const lambda& get() const { - return (*static_cast*>(this)); + return (*static_cast*>(this)); } }; } @@ -52,29 +59,34 @@ namespace rtl::dispatch struct functor_hop { - const lambda_hop* m_lambda = nullptr; + mutable const lambda_hop* m_lambda = nullptr; std::size_t m_recordId = detail::TypeId<>::None; std::size_t m_returnId = detail::TypeId<>::None; std::size_t m_signatureId = detail::TypeId<>::None; detail::methodQ m_qualifier = detail::methodQ::None; + void set_lambda(const lambda_hop* lambda) const + { + m_lambda = lambda; + } + template const functor& get() const { - return *(static_cast*>(this)); + return *(static_cast*>(this)); } template const functor_const& get_const() const { - return *(static_cast*>(this)); + return *(static_cast*>(this)); } template const functor_nonconst& get_nonconst() const { - return *(static_cast*>(this)); + return *(static_cast*>(this)); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index 5164719d..12782759 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -25,7 +25,7 @@ namespace rtl::dispatch return m_functor; } - return_t operator()(signature_ts&&...params) const + decltype(auto) operator()(signature_ts&&...params) const noexcept // TODO: handle exception. { return (*m_functor)(std::forward(params)...); } diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_const.h b/ReflectionTemplateLib/rtl/dispatch/functor_const.h index fff2d5ff..dea777bd 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor_const.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor_const.h @@ -27,7 +27,7 @@ namespace rtl::dispatch return m_functor; } - return_t operator()(const record_t& pTarget, signature_ts&&...params) const + decltype(auto) operator()(const record_t& pTarget, signature_ts&&...params) const noexcept // TODO: handle exception. { return (pTarget.*m_functor)(std::forward(params)...); } diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h b/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h index 646eef67..4ca1310a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h @@ -27,7 +27,7 @@ namespace rtl::dispatch return m_functor; } - return_t operator()(record_t& pTarget, signature_ts&&...params) const + decltype(auto) operator()(record_t& pTarget, signature_ts&&...params) const noexcept // TODO: handle exception. { return (pTarget.*m_functor)(std::forward(params)...); } diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index 10a54382..6a05ef00 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -22,7 +22,7 @@ namespace rtl::dispatch template struct lambda: public lambda_hop { - using lambda_t = std::function; + using lambda_t = std::function; template void init_ctor() const; @@ -41,18 +41,18 @@ namespace rtl::dispatch Return operator()(signature_ts&&...params) const { - return m_hopper(this, std::forward(params)...); + return m_hopper(*this, std::forward(params)...); } - private: - lambda(const functor_hop* fptr_hopper) { - detail::TypeId::get(m_argsTypeIds); + detail::TypeId::get(m_argumentsId); m_signatureId = detail::TypeId>::get(); m_functor = fptr_hopper; } - lambda_t m_hopper; + private: + + mutable lambda_t m_hopper; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp index bd980c3f..9a919ff2 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp @@ -24,20 +24,20 @@ namespace rtl::dispatch { if constexpr (std::is_same_v) { - m_hopper = [](const lambda_hop* hopper, signature_ts&&... params) -> Return + m_hopper = [](const lambda_hop& hopper, signature_ts&&... params) noexcept -> Return { - auto& functor = hopper->m_functor->get(); + auto& functor = hopper.functor().get(); functor(std::forward(params)...); - return{ error::None, RObject{} }; + return { error::None, RObject{} }; }; } else { - m_hopper = [](const lambda_hop* hopper, signature_ts&&...params) -> Return + m_hopper = [](const lambda_hop& hopper, signature_ts&&...params) noexcept -> Return { - auto& functor = hopper->m_functor->get(); + auto& functor = hopper.functor().get(); constexpr bool isConstCastSafe = (!traits::is_const_v); if constexpr (std::is_reference_v) @@ -45,11 +45,9 @@ namespace rtl::dispatch using T = traits::raw_t; const T& retObj = functor(std::forward(params)...); - return{ error::None, - builder::RObjectBuilder::template build( - &retObj, - std::nullopt, - isConstCastSafe) + return { error::None, + detail::RObjectBuilder::template + build(&retObj, std::nullopt, isConstCastSafe) }; } else { @@ -57,11 +55,9 @@ namespace rtl::dispatch auto&& retObj = functor(std::forward(params)...); using T = std::remove_cvref_t; - return{ error::None, - builder::RObjectBuilder::template build( - std::forward(retObj), - std::nullopt, - isConstCastSafe) + return { error::None, + detail::RObjectBuilder::template + build(std::forward(retObj), std::nullopt, isConstCastSafe) }; } }; diff --git a/ReflectionTemplateLib/rtl/rtl_traits.h b/ReflectionTemplateLib/rtl/rtl_traits.h index d2ccb404..cc2d25a3 100644 --- a/ReflectionTemplateLib/rtl/rtl_traits.h +++ b/ReflectionTemplateLib/rtl/rtl_traits.h @@ -27,6 +27,8 @@ namespace rtl { namespace traits { + using args_t = std::vector; + using Converter = std::function< std::any(const std::any&, const detail::EntityKind&, detail::EntityKind&) >; using ConverterPair = std::pair< std::size_t, Converter >; From d0df22470331c964c9ecf5c13d5e9a9ffb6adb8b Mon Sep 17 00:00:00 2001 From: neeraj Date: Thu, 18 Sep 2025 02:17:18 +0530 Subject: [PATCH 08/58] fixed cland/gcc compile error --- ReflectionTemplateLib/rtl/builder/SetupFunction.hpp | 2 +- ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index d01be707..ea170d1c 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -102,7 +102,7 @@ namespace rtl auto& lambda = lambdaCache.push(functor); - lambda.init_function<_returnType>(); + lambda.template init_function<_returnType>(); lambdaPtr = λ }; diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h b/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h index 9c8f4b5c..b0f8a3cc 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h +++ b/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h @@ -21,7 +21,7 @@ namespace rtl::dispatch struct functor_cache_nonconst { using fptr_t = return_t(record_t::*)(signature_ts...); - using functor_t = typename functor_nonconst; + using functor_t = functor_nonconst; static functor_cache_nonconst& get() { From 0fde83be0bfa36b0bc9a9975f8bdefda7036a836 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Thu, 18 Sep 2025 11:52:28 +0530 Subject: [PATCH 09/58] lambda refactored, std::function init with functor directly. --- RTLBenchmarkApp/src/ReflectedCall.cpp | 3 +- RTLBenchmarkApp/src/main.cpp | 2 +- .../rtl/builder/SetupFunction.hpp | 8 +-- .../rtl/cache/lambda_cache.h | 8 ++- ReflectionTemplateLib/rtl/dispatch/functor.h | 7 +-- ReflectionTemplateLib/rtl/dispatch/lambda.h | 54 +++++++++++++---- .../rtl/dispatch/lambda_copy_ctor.hpp | 4 +- .../rtl/dispatch/lambda_ctor.hpp | 4 +- .../rtl/dispatch/lambda_function.hpp | 59 ++++++++----------- .../rtl/dispatch/lambda_method_const.hpp | 4 +- .../rtl/dispatch/lambda_method_nonconst.hpp | 4 +- 11 files changed, 89 insertions(+), 68 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCall.cpp b/RTLBenchmarkApp/src/ReflectedCall.cpp index e62e3a11..d0225f3e 100644 --- a/RTLBenchmarkApp/src/ReflectedCall.cpp +++ b/RTLBenchmarkApp/src/ReflectedCall.cpp @@ -110,10 +110,9 @@ void ReflectedCall::get(benchmark::State& state) void ReflectedCall::new_design_set(benchmark::State& state) { static auto& hopper = (SendMessage.getFunctors()[0].m_lambda)->get(); - static bm::argStr_t&& argStr = bm::argStr_t(bm::g_longStr); for (auto _ : state) { - auto error = hopper(std::forward(argStr)).err; + auto error = hopper(bm::g_longStr).err; benchmark::DoNotOptimize(error); } } diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index 860bba04..e2de9214 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -9,8 +9,8 @@ BENCHMARK(NativeCall::set); BENCHMARK(StdFuncCall::set); -BENCHMARK(ReflectedCall::set); BENCHMARK(ReflectedCall::new_design_set); +BENCHMARK(ReflectedCall::set); BENCHMARK(StdFuncMethodCall::set); BENCHMARK(ReflectedMethodCall::set); diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index ea170d1c..c949782b 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -31,8 +31,8 @@ namespace rtl { return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { - bool isAmazing = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); - assert(isAmazing && "new type-system corrupted."); + //bool isAmazing = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + //assert(isAmazing && "new type-system corrupted."); pFunctor(std::forward<_signature>(params)...); return { error::None, RObject{} }; @@ -100,9 +100,7 @@ namespace rtl auto& lambdaCache = dispatch::lambda_cache<_signature...>::get(); - auto& lambda = lambdaCache.push(functor); - - lambda.template init_function<_returnType>(); + auto& lambda = lambdaCache.template push_function<_returnType>(functor); lambdaPtr = λ }; diff --git a/ReflectionTemplateLib/rtl/cache/lambda_cache.h b/ReflectionTemplateLib/rtl/cache/lambda_cache.h index 7c011a7e..9e0e1927 100644 --- a/ReflectionTemplateLib/rtl/cache/lambda_cache.h +++ b/ReflectionTemplateLib/rtl/cache/lambda_cache.h @@ -26,11 +26,15 @@ namespace rtl::dispatch return instance; } - const lambda& push(const functor_hop* fptr_hopper) + template + const lambda& push_function(const functor_hop* fptr_hopper) { - m_cache.push_back(lambda(fptr_hopper)); + m_cache.push_back(lambda::template create_function(fptr_hopper)); + const lambda& lambda_hop = m_cache.back(); + fptr_hopper->set_lambda(&lambda_hop); + return lambda_hop; } diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index 12782759..a3650e45 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -25,11 +25,6 @@ namespace rtl::dispatch return m_functor; } - decltype(auto) operator()(signature_ts&&...params) const noexcept // TODO: handle exception. - { - return (*m_functor)(std::forward(params)...); - } - functor(fptr_t fptr) :m_functor(fptr) { m_returnId = detail::TypeId::get(); @@ -38,6 +33,6 @@ namespace rtl::dispatch private: - fptr_t m_functor; + const fptr_t m_functor; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index 6a05ef00..469e701a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -25,34 +25,66 @@ namespace rtl::dispatch using lambda_t = std::function; template - void init_ctor() const; + static lambda create_ctor(const functor_hop* fptr_hopper) + { + return lambda(fptr_hopper, &ctor); + } template - void init_cloner() const; + static lambda create_copy_ctor(const functor_hop* fptr_hopper) + { + return lambda(fptr_hopper, ©_ctor); + } template - void init_function() const; + static lambda create_function(const functor_hop* fptr_hopper) + { + return lambda(fptr_hopper, &function); + } template - void init_method_const() const; + static lambda create_method_const(const functor_hop* fptr_hopper) + { + return lambda(fptr_hopper, &method_const); + } template - void init_method_nonconst() const; - - Return operator()(signature_ts&&...params) const + static lambda create_method_nonconst(const functor_hop* fptr_hopper) { - return m_hopper(*this, std::forward(params)...); + return lambda(fptr_hopper, &method_nonconst); + } + + template + decltype(auto) operator()(args_t&&...params) const noexcept + { + return m_hopper(*this, std::forward(params)...); } - lambda(const functor_hop* fptr_hopper) + private: + + const lambda_t m_hopper; + + lambda(const functor_hop* fptr_hopper, lambda_t hopper) noexcept + : m_hopper(std::move(hopper)) { detail::TypeId::get(m_argumentsId); m_signatureId = detail::TypeId>::get(); m_functor = fptr_hopper; } - private: + template + static Return ctor(const lambda_hop&, signature_ts&&...) noexcept; + + template + static Return copy_ctor(const lambda_hop&, signature_ts&&...) noexcept; - mutable lambda_t m_hopper; + template + static Return function(const lambda_hop&, signature_ts&&...) noexcept; + + template + static Return method_const(const lambda_hop&, signature_ts&&...) noexcept; + + template + static Return method_nonconst(const lambda_hop&, signature_ts&&...) noexcept; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_copy_ctor.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_copy_ctor.hpp index dd8b664c..2406fd6e 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_copy_ctor.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_copy_ctor.hpp @@ -19,8 +19,8 @@ namespace rtl::dispatch { template template - inline void lambda::init_cloner() const + inline Return lambda::copy_ctor(const lambda_hop&, signature_ts&&...) noexcept { - + return { error::EmptyRObject, RObject{} }; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp index e864c2f7..e42ef552 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp @@ -18,8 +18,8 @@ namespace rtl::dispatch { template template - inline void lambda::init_ctor() const + inline Return lambda::ctor(const lambda_hop&, signature_ts&&...) noexcept { - + return { error::EmptyRObject, RObject{} }; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp index 9a919ff2..64392aec 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp @@ -14,53 +14,46 @@ #include #include "lambda.h" +#include "functor.h" #include "RObjectBuilder.hpp" namespace rtl::dispatch { template template - inline void lambda::init_function() const + inline Return lambda::function(const lambda_hop& hopper, signature_ts&&...params) noexcept { + auto functor = hopper.functor().get().get(); + if constexpr (std::is_same_v) { - m_hopper = [](const lambda_hop& hopper, signature_ts&&... params) noexcept -> Return - { - auto& functor = hopper.functor().get(); - - functor(std::forward(params)...); + (*functor)(std::forward(params)...); - return { error::None, RObject{} }; - }; + return { error::None, RObject{} }; } else { - m_hopper = [](const lambda_hop& hopper, signature_ts&&...params) noexcept -> Return + constexpr bool isConstCastSafe = (!traits::is_const_v); + if constexpr (std::is_reference_v) { - auto& functor = hopper.functor().get(); - - constexpr bool isConstCastSafe = (!traits::is_const_v); - if constexpr (std::is_reference_v) - { - using T = traits::raw_t; - const T& retObj = functor(std::forward(params)...); - - return { error::None, - detail::RObjectBuilder::template - build(&retObj, std::nullopt, isConstCastSafe) - }; - } - else { - - auto&& retObj = functor(std::forward(params)...); - using T = std::remove_cvref_t; - - return { error::None, - detail::RObjectBuilder::template - build(std::forward(retObj), std::nullopt, isConstCastSafe) - }; - } - }; + using T = traits::raw_t; + const T& retObj = functor(std::forward(params)...); + + return { error::None, + detail::RObjectBuilder::template + build(&retObj, std::nullopt, isConstCastSafe) + }; + } + else { + + auto&& retObj = functor(std::forward(params)...); + using T = std::remove_cvref_t; + + return { error::None, + detail::RObjectBuilder::template + build(std::forward(retObj), std::nullopt, isConstCastSafe) + }; + } } } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp index d6c1a39e..8e1137a0 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp @@ -18,8 +18,8 @@ namespace rtl::dispatch { template template - inline void lambda::init_method_const() const + inline Return lambda::method_const(const lambda_hop&, signature_ts&&...) noexcept { - + return { error::EmptyRObject, RObject{} }; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp index 9203bfd7..befceb5a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp @@ -17,8 +17,8 @@ namespace rtl::dispatch { template template - inline void lambda::init_method_nonconst() const + inline Return lambda::method_nonconst(const lambda_hop&, signature_ts&&...) noexcept { - + return { error::EmptyRObject, RObject{} }; } } \ No newline at end of file From 387fcaad74da40be5a0a253ebd856b26c2cd53fe Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Fri, 19 Sep 2025 01:23:48 +0530 Subject: [PATCH 10/58] return-type erased from cache/functor/lambda containers. --- .../rtl/builder/SetupFunction.hpp | 21 +++--- .../rtl/builder/SetupMethod.hpp | 72 ++++++++++++++----- .../rtl/cache/functor_cache.h | 26 ++++--- .../rtl/cache/functor_cache_const.h | 29 ++++---- .../rtl/cache/functor_cache_nonconst.h | 28 ++++---- .../rtl/cache/lambda_cache.h | 25 +++++-- .../rtl/dispatch/dispatch_interface.h | 53 +++++++------- ReflectionTemplateLib/rtl/dispatch/functor.h | 28 ++++++-- .../rtl/dispatch/functor_const.h | 25 ++++--- .../rtl/dispatch/functor_nonconst.h | 25 ++++--- ReflectionTemplateLib/rtl/dispatch/lambda.h | 23 +++--- .../rtl/dispatch/lambda_function.hpp | 2 +- .../rtl/dispatch/lambda_method_const.hpp | 1 - ReflectionTemplateLib/rtl/rtl_traits.h | 2 - 14 files changed, 231 insertions(+), 129 deletions(-) diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index c949782b..264337cc 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -31,8 +31,8 @@ namespace rtl { return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { - //bool isAmazing = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); - //assert(isAmazing && "new type-system corrupted."); + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + assert(isAllGood && "new type-id-system not working."); pFunctor(std::forward<_signature>(params)...); return { error::None, RObject{} }; @@ -49,8 +49,8 @@ namespace rtl this is stored in _derivedType's (FunctorContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, _signature&&...params)-> Return { - bool isAmazing = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); - assert(isAmazing && "new type-system corrupted."); + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + assert(isAllGood && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); @@ -94,11 +94,11 @@ namespace rtl const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& functorCache = dispatch::functor_cache<_returnType, _signature...>::get(); + auto& functorCache = dispatch::functor_cache<_signature...>::instance(); - const dispatch::functor_hop* functor = functorCache.push(pFunctor, pIndex); + const dispatch::functor_hop* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambdaCache = dispatch::lambda_cache<_signature...>::get(); + auto& lambdaCache = dispatch::lambda_cache<_signature...>::instance(); auto& lambda = lambdaCache.template push_function<_returnType>(functor); @@ -107,11 +107,14 @@ namespace rtl const auto& getIndex = [&]()-> std::size_t { - auto& functorCache = dispatch::functor_cache<_returnType, _signature...>::get(); - auto [functor, lambdaIndex] = functorCache.find(pFunctor); + auto& functorCache = dispatch::functor_cache<_signature...>::instance(); + + auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); + if (lambdaIndex != rtl::index_none) { lambdaPtr = functor->m_lambda; } + return lambdaIndex; }; diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 6cc63e50..1ea5f350 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -17,8 +17,11 @@ #include "rtl_typeid.h" #include "SetupMethod.h" #include "RObjectBuilder.hpp" + #include "functor_cache_const.h" #include "functor_cache_nonconst.h" +#include "lambda_method_const.hpp" +#include "lambda_method_nonconst.hpp" namespace rtl::detail { @@ -31,6 +34,9 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + assert(isAllGood && "new type-id-system not working."); + if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; } @@ -51,6 +57,9 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + assert(isAllGood && "new type-id-system not working."); + if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; } @@ -92,6 +101,9 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + assert(isAllGood && "new type-id-system not working."); + const _recordType& target = pTargetObj.view<_recordType>()->get(); (target.*pFunctor)(std::forward<_signature>(params)...); return { error::None, RObject{} }; @@ -108,6 +120,9 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + assert(isAllGood && "new type-id-system not working."); + constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); //'target' is const and 'pFunctor' is const-member-function. const _recordType& target = pTargetObj.view<_recordType>()->get(); @@ -148,18 +163,31 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...)) { - auto& functorCache = dispatch::functor_cache_nonconst<_recordType, _returnType, _signature...>::get(); + const dispatch::lambda_hop* lambdaPtr = nullptr; - // called from '_derivedType' (MethodContainer) - const auto& updateIndex = [&](std::size_t pIndex)->void + const auto& updateIndex = [&](std::size_t pIndex)-> void { - functorCache.push(pFunctor, pIndex); + auto& functorCache = dispatch::functor_cache_nonconst<_recordType, _signature...>::instance(); + + const dispatch::functor_hop* functor = functorCache.template push<_returnType>(pFunctor, pIndex); + + auto& lambdaCache = dispatch::lambda_cache<_signature...>::instance(); + + auto& lambda = lambdaCache.template push_method_nonconst<_recordType, _returnType>(functor); + + lambdaPtr = λ }; - // called from '_derivedType' (MethodContainer) const auto& getIndex = [&]()-> std::size_t { - std::size_t lambdaIndex = functorCache.find(pFunctor); + auto& functorCache = dispatch::functor_cache_nonconst<_recordType, _signature...>::instance(); + + auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); + + if (lambdaIndex != rtl::index_none) { + lambdaPtr = functor->m_lambda; + } + return lambdaIndex; }; @@ -178,7 +206,7 @@ namespace rtl::detail TypeId<_recordType>::get(), _derivedType::getContainerId(), _derivedType::template getSignatureStr<_recordType, _returnType>(), - nullptr + lambdaPtr }; } else @@ -192,7 +220,7 @@ namespace rtl::detail TypeId<_recordType>::get(), _derivedType::getContainerId(), _derivedType::template getSignatureStr<_recordType, _returnType>(), - nullptr + lambdaPtr }; } } @@ -211,19 +239,31 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const) { - auto& functorCache = dispatch::functor_cache_const<_recordType, _returnType, _signature...>::get(); + const dispatch::lambda_hop* lambdaPtr = nullptr; - // called from '_derivedType' (MethodContainer) const auto& updateIndex = [&](std::size_t pIndex)-> void { - //functorIndex = functorCache.get().size(); - functorCache.push(pFunctor, pIndex); + auto& functorCache = dispatch::functor_cache_const<_recordType, _signature...>::instance(); + + const dispatch::functor_hop* functor = functorCache.template push<_returnType>(pFunctor, pIndex); + + auto& lambdaCache = dispatch::lambda_cache<_signature...>::instance(); + + auto& lambda = lambdaCache.template push_method_const<_recordType, _returnType>(functor); + + lambdaPtr = λ }; - // called from '_derivedType' (MethodContainer) const auto& getIndex = [&]()-> std::size_t { - std::size_t lambdaIndex = functorCache.find(pFunctor); + auto& functorCache = dispatch::functor_cache_const<_recordType, _signature...>::instance(); + + auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); + + if (lambdaIndex != rtl::index_none) { + lambdaPtr = functor->m_lambda; + } + return lambdaIndex; }; @@ -243,7 +283,7 @@ namespace rtl::detail TypeId<_recordType>::get(), _derivedType::getContainerId(), _derivedType::template getSignatureStr<_recordType, _returnType>(), - nullptr//&lambdaCache + lambdaPtr }; } else @@ -257,7 +297,7 @@ namespace rtl::detail TypeId<_recordType>::get(), _derivedType::getContainerId(), _derivedType::template getSignatureStr<_recordType, _returnType>(), - nullptr// &lambdaCache + lambdaPtr }; } } diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache.h b/ReflectionTemplateLib/rtl/cache/functor_cache.h index 13fd39b7..4ba654a8 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache.h +++ b/ReflectionTemplateLib/rtl/cache/functor_cache.h @@ -17,30 +17,34 @@ namespace rtl::dispatch { - template + template struct functor_cache { - using fptr_t = return_t(*)(signature_ts...); - using functor_t = functor; + using functor_t = functor; - static functor_cache& get() + static const functor_cache& instance() { - static functor_cache instance; - return instance; + static functor_cache instance_; + return instance_; } - const functor_hop* push(const functor_t& functor, std::size_t lambda_index) + template + const functor_hop* push(return_t(*fptr)(signature_ts...), std::size_t lambda_index) const { - m_cache.emplace_back(std::make_pair(functor, lambda_index)); + using voidfn_t = typename functor::voidfn_t; + + auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); + m_cache.emplace_back(std::make_pair(functor , lambda_index)); return &(m_cache.back().first); } - std::pair find(fptr_t fptr) + template + std::pair find(return_t(*fptr)(signature_ts...)) const { for (auto& itr : m_cache) { const auto& functor = itr.first; - if (fptr == functor.get()) { + if (functor.template is_same(fptr)) { return { &itr.first, itr.second }; } } @@ -55,7 +59,7 @@ namespace rtl::dispatch private: // No reallocation occurs; original objects stay intact - std::list> m_cache; + mutable std::list> m_cache; functor_cache() {} }; diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_const.h b/ReflectionTemplateLib/rtl/cache/functor_cache_const.h index 7d1af246..a7a351a3 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache_const.h +++ b/ReflectionTemplateLib/rtl/cache/functor_cache_const.h @@ -17,37 +17,40 @@ namespace rtl::dispatch { - template + template struct functor_cache_const { - using fptr_t = return_t(record_t::*)(signature_ts...) const; - using functor_t = functor_const; + using functor_t = functor_const; - static functor_cache_const& get() + static const functor_cache_const& instance() { - static functor_cache_const instance; - return instance; + static functor_cache_const instance_; + return instance_; } - const functor_hop* push(const functor_t& functor, std::size_t lambda_index) + template + const functor_hop* push(return_t(record_t::* fptr)(signature_ts...) const, std::size_t lambda_index) const { + using voidfn_t = typename functor_const::voidfn_t; + auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); m_cache.emplace_back(std::make_pair(functor, lambda_index)); return &(m_cache.back().first); + } - std::size_t find(fptr_t fptr) + template + std::pair find(return_t(record_t::* fptr)(signature_ts...) const) const { for (auto& itr : m_cache) { const auto& functor = itr.first; - if (fptr == functor.get()) { - return itr.second; + if (functor.template is_same(fptr)) { + return { &itr.first, itr.second }; } } - return rtl::index_none; + return { nullptr, rtl::index_none }; } - functor_cache_const(functor_cache_const&&) = delete; functor_cache_const(const functor_cache_const&) = delete; functor_cache_const& operator=(functor_cache_const&&) = delete; @@ -56,7 +59,7 @@ namespace rtl::dispatch private: // No reallocation occurs; original objects stay intact - std::list> m_cache; + mutable std::list> m_cache; functor_cache_const() {} }; diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h b/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h index b0f8a3cc..e9a240e9 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h +++ b/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h @@ -17,37 +17,39 @@ namespace rtl::dispatch { - template + template struct functor_cache_nonconst { - using fptr_t = return_t(record_t::*)(signature_ts...); - using functor_t = functor_nonconst; + using functor_t = functor_nonconst; - static functor_cache_nonconst& get() + static const functor_cache_nonconst& instance() { - static functor_cache_nonconst instance; - return instance; + static const functor_cache_nonconst instance_; + return instance_; } - const functor_hop* push(const functor_t& functor, std::size_t lambda_index) + template + const functor_hop* push(return_t(record_t::* fptr)(signature_ts...), std::size_t lambda_index) const { + using voidfn_t = typename functor_nonconst::voidfn_t; + auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); m_cache.emplace_back(std::make_pair(functor, lambda_index)); return &(m_cache.back().first); } - std::size_t find(fptr_t fptr) + template + std::pair find(return_t(record_t::* fptr)(signature_ts...)) const { for (auto& itr : m_cache) { const auto& functor = itr.first; - if (fptr == functor.get()) { - return itr.second; + if (functor.template is_same(fptr)) { + return { &itr.first, itr.second }; } } - return rtl::index_none; + return { nullptr, rtl::index_none }; } - functor_cache_nonconst(functor_cache_nonconst&&) = delete; functor_cache_nonconst(const functor_cache_nonconst&) = delete; functor_cache_nonconst& operator=(functor_cache_nonconst&&) = delete; @@ -56,7 +58,7 @@ namespace rtl::dispatch private: // No reallocation occurs; original objects stay intact - std::list> m_cache; + mutable std::list> m_cache; functor_cache_nonconst() {} }; diff --git a/ReflectionTemplateLib/rtl/cache/lambda_cache.h b/ReflectionTemplateLib/rtl/cache/lambda_cache.h index 9e0e1927..21d249f1 100644 --- a/ReflectionTemplateLib/rtl/cache/lambda_cache.h +++ b/ReflectionTemplateLib/rtl/cache/lambda_cache.h @@ -20,21 +20,36 @@ namespace rtl::dispatch template struct lambda_cache { - static lambda_cache& get() + static lambda_cache& instance() { - static lambda_cache instance; - return instance; + static lambda_cache instance_; + return instance_; } template const lambda& push_function(const functor_hop* fptr_hopper) { m_cache.push_back(lambda::template create_function(fptr_hopper)); + const lambda& lambda_hop = m_cache.back(); + fptr_hopper->set_lambda(&lambda_hop); + return lambda_hop; + } + template + const lambda& push_method_const(const functor_hop* fptr_hopper) + { + m_cache.push_back(lambda::template create_method_const(fptr_hopper)); + const lambda& lambda_hop = m_cache.back(); + fptr_hopper->set_lambda(&lambda_hop); + return lambda_hop; + } + + template + const lambda& push_method_nonconst(const functor_hop* fptr_hopper) + { + m_cache.push_back(lambda::template create_method_nonconst(fptr_hopper)); const lambda& lambda_hop = m_cache.back(); - fptr_hopper->set_lambda(&lambda_hop); - return lambda_hop; } diff --git a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h b/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h index 7ecb6723..eee70c23 100644 --- a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h +++ b/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h @@ -26,12 +26,6 @@ namespace rtl::dispatch struct lambda_hop { - std::size_t m_signatureId = detail::TypeId<>::None; - - traits::args_t m_argumentsId = {}; - - const functor_hop* m_functor = nullptr; - const functor_hop& functor() const { return *m_functor; @@ -42,51 +36,60 @@ namespace rtl::dispatch { return (*static_cast*>(this)); } + +// protected: + + const functor_hop* m_functor = nullptr; + std::size_t m_returnId = detail::TypeId<>::None; + std::size_t m_signatureId = detail::TypeId<>::None; + std::vector m_argumentsId = {}; }; } namespace rtl::dispatch { - template + template struct functor; - template + template struct functor_const; - template + template struct functor_nonconst; struct functor_hop { - mutable const lambda_hop* m_lambda = nullptr; - - std::size_t m_recordId = detail::TypeId<>::None; - std::size_t m_returnId = detail::TypeId<>::None; - std::size_t m_signatureId = detail::TypeId<>::None; - detail::methodQ m_qualifier = detail::methodQ::None; - void set_lambda(const lambda_hop* lambda) const { m_lambda = lambda; } - template - const functor& get() const + template + const functor& get() const { - return *(static_cast*>(this)); + return *(static_cast*>(this)); } - template - const functor_const& get_const() const + template + const functor_const& get_const() const { - return *(static_cast*>(this)); + return *(static_cast*>(this)); } - template - const functor_nonconst& get_nonconst() const + template + const functor_nonconst& get_nonconst() const { - return *(static_cast*>(this)); + return *(static_cast*>(this)); } + +// protected: + + mutable const lambda_hop* m_lambda = nullptr; + + std::size_t m_recordId = detail::TypeId<>::None; + std::size_t m_returnId = detail::TypeId<>::None; + std::size_t m_signatureId = detail::TypeId<>::None; + detail::methodQ m_qualifier = detail::methodQ::None; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index a3650e45..886551e6 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -15,24 +15,38 @@ namespace rtl::dispatch { - template + template struct functor: public functor_hop { - using fptr_t = return_t(*)(signature_ts...); + using voidfn_t = void(*)(signature_ts...); - fptr_t get() const + template + decltype(auto) get(std::size_t returnId) const { - return m_functor; + using fptr_t = return_t(*)(signature_ts...); + if (returnId == m_returnId) + { + return reinterpret_cast(m_functor); + } + return static_cast(nullptr); } - functor(fptr_t fptr) :m_functor(fptr) + template + bool is_same(return_t(*fptr)(signature_ts...)) const { - m_returnId = detail::TypeId::get(); + return (m_functor == reinterpret_cast(fptr)); + } + + functor(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) + { + m_returnId = returnId; m_signatureId = detail::TypeId>::get(); } + functor(const functor&) = default; + private: - const fptr_t m_functor; + const voidfn_t m_functor; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_const.h b/ReflectionTemplateLib/rtl/dispatch/functor_const.h index dea777bd..7a0ae4b9 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor_const.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor_const.h @@ -17,29 +17,36 @@ namespace rtl::dispatch { - template + template struct functor_const : public functor_hop { - using fptr_t = return_t(record_t::*)(signature_ts...) const; + using voidfn_t = void(record_t::*)(signature_ts...) const; - fptr_t get() const + template + decltype(auto) get(std::size_t returnId) const { - return m_functor; + using fptr_t = return_t(record_t::*)(signature_ts...); + if (returnId == m_returnId) + { + return reinterpret_cast(m_functor); + } + return static_cast(nullptr); } - decltype(auto) operator()(const record_t& pTarget, signature_ts&&...params) const noexcept // TODO: handle exception. + template + bool is_same(return_t(record_t::*fptr)(signature_ts...) const) const { - return (pTarget.*m_functor)(std::forward(params)...); + return (m_functor == reinterpret_cast(fptr)); } - functor_const(fptr_t fptr) :m_functor(fptr) + functor_const(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) { - m_returnId = detail::TypeId::get(); + m_returnId = returnId; m_signatureId = detail::TypeId>::get(); } private: - fptr_t m_functor; + const voidfn_t m_functor; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h b/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h index 4ca1310a..f42e3e64 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h @@ -17,29 +17,36 @@ namespace rtl::dispatch { - template + template struct functor_nonconst : public functor_hop { - using fptr_t = return_t(record_t::*)(signature_ts...); + using voidfn_t = void(record_t::*)(signature_ts...); - fptr_t get() const + template + decltype(auto) get(std::size_t returnId) const { - return m_functor; + using fptr_t = return_t(record_t::*)(signature_ts...); + if (returnId == m_returnId) + { + return reinterpret_cast(m_functor); + } + return static_cast(nullptr); } - decltype(auto) operator()(record_t& pTarget, signature_ts&&...params) const noexcept // TODO: handle exception. + template + bool is_same(return_t(record_t::* fptr)(signature_ts...)) const { - return (pTarget.*m_functor)(std::forward(params)...); + return (m_functor == reinterpret_cast(fptr)); } - functor_nonconst(fptr_t fptr) :m_functor(fptr) + functor_nonconst(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) { - m_returnId = detail::TypeId::get(); + m_returnId = returnId; m_signatureId = detail::TypeId>::get(); } private: - fptr_t m_functor; + const voidfn_t m_functor; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index 469e701a..ddde9833 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -13,6 +13,7 @@ #include #include +#include #include "forward_decls.h" #include "dispatch_interface.h" @@ -27,31 +28,36 @@ namespace rtl::dispatch template static lambda create_ctor(const functor_hop* fptr_hopper) { - return lambda(fptr_hopper, &ctor); + std::size_t returnId = detail::TypeId::get(); + return lambda(returnId, fptr_hopper, &ctor); } template static lambda create_copy_ctor(const functor_hop* fptr_hopper) { - return lambda(fptr_hopper, ©_ctor); + std::size_t returnId = detail::TypeId::get(); + return lambda(returnId, fptr_hopper, ©_ctor); } template static lambda create_function(const functor_hop* fptr_hopper) { - return lambda(fptr_hopper, &function); + std::size_t returnId = detail::TypeId::get(); + return lambda(returnId, fptr_hopper, &function); } template static lambda create_method_const(const functor_hop* fptr_hopper) { - return lambda(fptr_hopper, &method_const); + std::size_t returnId = detail::TypeId::get(); + return lambda(returnId, fptr_hopper, &method_const); } template static lambda create_method_nonconst(const functor_hop* fptr_hopper) { - return lambda(fptr_hopper, &method_nonconst); + std::size_t returnId = detail::TypeId::get(); + return lambda(returnId, fptr_hopper, &method_nonconst); } template @@ -64,12 +70,13 @@ namespace rtl::dispatch const lambda_t m_hopper; - lambda(const functor_hop* fptr_hopper, lambda_t hopper) noexcept + lambda(std::size_t returnId, const functor_hop* functor, lambda_t hopper) noexcept : m_hopper(std::move(hopper)) { - detail::TypeId::get(m_argumentsId); + m_functor = functor; + m_returnId = returnId; m_signatureId = detail::TypeId>::get(); - m_functor = fptr_hopper; + detail::TypeId::get(m_argumentsId); } template diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp index 64392aec..d972a882 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp @@ -23,7 +23,7 @@ namespace rtl::dispatch template inline Return lambda::function(const lambda_hop& hopper, signature_ts&&...params) noexcept { - auto functor = hopper.functor().get().get(); + auto functor = hopper.functor().get().get(hopper.m_returnId); if constexpr (std::is_same_v) { diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp index 8e1137a0..79fa3c5f 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp @@ -12,7 +12,6 @@ #pragma once #include "lambda.h" -#include "RObjectBuilder.hpp" namespace rtl::dispatch { diff --git a/ReflectionTemplateLib/rtl/rtl_traits.h b/ReflectionTemplateLib/rtl/rtl_traits.h index cc2d25a3..d2ccb404 100644 --- a/ReflectionTemplateLib/rtl/rtl_traits.h +++ b/ReflectionTemplateLib/rtl/rtl_traits.h @@ -27,8 +27,6 @@ namespace rtl { namespace traits { - using args_t = std::vector; - using Converter = std::function< std::any(const std::any&, const detail::EntityKind&, detail::EntityKind&) >; using ConverterPair = std::pair< std::size_t, Converter >; From d9aef490cffaf5746c42c9635cf9a88bf63464e1 Mon Sep 17 00:00:00 2001 From: neeraj Date: Fri, 19 Sep 2025 01:37:29 +0530 Subject: [PATCH 11/58] fixed cland/gcc compile error --- ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp index d972a882..3a183df9 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp @@ -23,7 +23,7 @@ namespace rtl::dispatch template inline Return lambda::function(const lambda_hop& hopper, signature_ts&&...params) noexcept { - auto functor = hopper.functor().get().get(hopper.m_returnId); + auto functor = hopper.functor().get().template get(hopper.m_returnId); if constexpr (std::is_same_v) { From 7c1af2415ea11f90a37ac810ec9f941d4f517c7d Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Fri, 19 Sep 2025 09:42:01 +0530 Subject: [PATCH 12/58] enabled reflective call with known return-type --- RTLBenchmarkApp/src/ReflectedCall.cpp | 33 ++++++-- .../rtl/builder/SetupFunction.hpp | 12 +-- .../rtl/builder/SetupMethod.hpp | 26 +----- .../rtl/dispatch/CMakeLists.txt | 9 +-- ReflectionTemplateLib/rtl/dispatch/hopper.h | 80 +++++++++++++++++++ .../{lambda_ctor.hpp => hopper_const.h} | 12 +-- ...mbda_method_nonconst.hpp => hopper_ctor.h} | 18 ++++- ...lambda_copy_ctor.hpp => hopper_nonconst.h} | 13 +-- ReflectionTemplateLib/rtl/dispatch/lambda.h | 45 +++++++---- .../rtl/dispatch/lambda_function.hpp | 59 -------------- .../rtl/dispatch/lambda_method_const.hpp | 24 ------ 11 files changed, 175 insertions(+), 156 deletions(-) create mode 100644 ReflectionTemplateLib/rtl/dispatch/hopper.h rename ReflectionTemplateLib/rtl/dispatch/{lambda_ctor.hpp => hopper_const.h} (76%) rename ReflectionTemplateLib/rtl/dispatch/{lambda_method_nonconst.hpp => hopper_ctor.h} (65%) rename ReflectionTemplateLib/rtl/dispatch/{lambda_copy_ctor.hpp => hopper_nonconst.h} (76%) delete mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp delete mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp diff --git a/RTLBenchmarkApp/src/ReflectedCall.cpp b/RTLBenchmarkApp/src/ReflectedCall.cpp index d0225f3e..84cc6370 100644 --- a/RTLBenchmarkApp/src/ReflectedCall.cpp +++ b/RTLBenchmarkApp/src/ReflectedCall.cpp @@ -5,6 +5,12 @@ #include "ReflectedCall.h" #include "BenchMark.h" + +namespace bm +{ + extern std::optional g_work_done; +} + namespace cxx { extern const rtl::CxxMirror& mirror(); @@ -48,17 +54,29 @@ namespace auto err = SendMessage(bm::g_longStr).err; if (err != rtl::error::None) { - std::cout << "[1] error: "<< rtl::to_string(err)<<"\n"; + std::cout << "[0] error: "<< rtl::to_string(err)<<"\n"; } return 0; }; + + static auto _test4 = []() + { + auto& hopper = (SendMessage.getFunctors()[0].m_lambda)->get(); + //auto err = hopper(bm::g_longStr).err; + //if (err != rtl::error::None) { + // std::cout << "[4] error: " << rtl::to_string(err) << "\n"; + //} + return hopper; + }; + + static auto _test1 = []() { auto err = NodeSendMessage(nodeObj)(bm::g_longStr).err; if (err != rtl::error::None) { - std::cout << "[2] error: " << rtl::to_string(err) << "\n"; + std::cout << "[1] error: " << rtl::to_string(err) << "\n"; } return 0; }; @@ -68,7 +86,7 @@ namespace auto err = GetMessage(bm::g_longStr).err; if (err != rtl::error::None) { - std::cout << "[3] error: " << rtl::to_string(err) << "\n"; + std::cout << "[2] error: " << rtl::to_string(err) << "\n"; } return 0; }; @@ -78,7 +96,7 @@ namespace auto err = NodeGetMessage(nodeObj)(bm::g_longStr).err; if (err != rtl::error::None) { - std::cout << "[4] error: " << rtl::to_string(err) << "\n"; + std::cout << "[3] error: " << rtl::to_string(err) << "\n"; } return 0; }; @@ -109,11 +127,12 @@ void ReflectedCall::get(benchmark::State& state) void ReflectedCall::new_design_set(benchmark::State& state) { - static auto& hopper = (SendMessage.getFunctors()[0].m_lambda)->get(); + static const auto& hopper = _test4(); for (auto _ : state) { - auto error = hopper(bm::g_longStr).err; - benchmark::DoNotOptimize(error); + hopper.call(bm::g_longStr); + //auto ret = hopper(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index 264337cc..ac0cc135 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -15,7 +15,6 @@ #include "lambda_cache.h" #include "functor_cache.h" -#include "lambda_function.hpp" #include "SetupFunction.h" #include "RObjectBuilder.hpp" @@ -94,27 +93,20 @@ namespace rtl const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& functorCache = dispatch::functor_cache<_signature...>::instance(); - - const dispatch::functor_hop* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambdaCache = dispatch::lambda_cache<_signature...>::instance(); - + auto& functorCache = dispatch::functor_cache<_signature...>::instance(); + auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); auto& lambda = lambdaCache.template push_function<_returnType>(functor); - lambdaPtr = λ }; const auto& getIndex = [&]()-> std::size_t { auto& functorCache = dispatch::functor_cache<_signature...>::instance(); - auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); - if (lambdaIndex != rtl::index_none) { lambdaPtr = functor->m_lambda; } - return lambdaIndex; }; diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 1ea5f350..f420f873 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -20,8 +20,6 @@ #include "functor_cache_const.h" #include "functor_cache_nonconst.h" -#include "lambda_method_const.hpp" -#include "lambda_method_nonconst.hpp" namespace rtl::detail { @@ -164,30 +162,22 @@ namespace rtl::detail inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...)) { const dispatch::lambda_hop* lambdaPtr = nullptr; - const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& functorCache = dispatch::functor_cache_nonconst<_recordType, _signature...>::instance(); - - const dispatch::functor_hop* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambdaCache = dispatch::lambda_cache<_signature...>::instance(); - + auto& functorCache = dispatch::functor_cache_nonconst<_recordType, _signature...>::instance(); + auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); auto& lambda = lambdaCache.template push_method_nonconst<_recordType, _returnType>(functor); - lambdaPtr = λ }; const auto& getIndex = [&]()-> std::size_t { auto& functorCache = dispatch::functor_cache_nonconst<_recordType, _signature...>::instance(); - auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); - if (lambdaIndex != rtl::index_none) { lambdaPtr = functor->m_lambda; } - return lambdaIndex; }; @@ -240,30 +230,22 @@ namespace rtl::detail inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const) { const dispatch::lambda_hop* lambdaPtr = nullptr; - const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& functorCache = dispatch::functor_cache_const<_recordType, _signature...>::instance(); - - const dispatch::functor_hop* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambdaCache = dispatch::lambda_cache<_signature...>::instance(); - + auto& functorCache = dispatch::functor_cache_const<_recordType, _signature...>::instance(); + auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); auto& lambda = lambdaCache.template push_method_const<_recordType, _returnType>(functor); - lambdaPtr = λ }; const auto& getIndex = [&]()-> std::size_t { auto& functorCache = dispatch::functor_cache_const<_recordType, _signature...>::instance(); - auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); - if (lambdaIndex != rtl::index_none) { lambdaPtr = functor->m_lambda; } - return lambdaIndex; }; diff --git a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt index 6fa05029..5f1ba12a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt @@ -9,11 +9,10 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/functor_nonconst.h" "${CMAKE_CURRENT_SOURCE_DIR}/lambda.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_ctor.hpp" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function.hpp" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_copy_ctor.hpp" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method_const.hpp" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method_nonconst.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/hopper.h" + "${CMAKE_CURRENT_SOURCE_DIR}/hopper_ctor.h" + "${CMAKE_CURRENT_SOURCE_DIR}/hopper_const.h" + "${CMAKE_CURRENT_SOURCE_DIR}/hoppert_nonconst.h" "${CMAKE_CURRENT_SOURCE_DIR}/CallReflector.h" "${CMAKE_CURRENT_SOURCE_DIR}/FunctionCaller.h" diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper.h b/ReflectionTemplateLib/rtl/dispatch/hopper.h new file mode 100644 index 00000000..62a26bbb --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/hopper.h @@ -0,0 +1,80 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "lambda.h" +#include "functor.h" +//#include "RObjectBuilder.hpp" + +namespace rtl::dispatch +{ + template + struct hopper + { + template + static decltype(auto) function(const lambda_hop& lambda_ref, signature_ts&&...params) noexcept + { + auto functor = lambda_ref.functor().template get().template get(lambda_ref.m_returnId); + if constexpr (std::is_same_v) { + (*functor)(std::forward(params)...); + } + else { + return (*functor)(std::forward(params)...); + } + } + + template requires (is_void_t == true) + static Return function(const lambda_hop& lambda_ref, signature_ts&&...params) noexcept + { + if constexpr (std::is_same_v) { + auto functor = lambda_ref.functor().template get().template get(lambda_ref.m_returnId); + (*functor)(std::forward(params)...); + } + else { + static_assert("return-type mismatch."); + } + return { error::None, RObject{} }; + } + + template requires (is_void_t == false) + static Return function(const lambda_hop& lambda_ref, signature_ts&&...params) noexcept + { + constexpr bool isConstCastSafe = (!traits::is_const_v); + + auto functor = lambda_ref.functor().template get().template get(lambda_ref.m_returnId); + + if constexpr (std::is_reference_v) + { + using T = traits::raw_t; + const T& retObj = functor(std::forward(params)...); + + //return { error::None, + // detail::RObjectBuilder::template + // build(&retObj, std::nullopt, isConstCastSafe) + //}; + } + else { + + auto&& retObj = functor(std::forward(params)...); + using T = std::remove_cvref_t; + + //return { error::None, + // detail::RObjectBuilder::template + // build(std::forward(retObj), std::nullopt, isConstCastSafe) + //}; + } + return { error::None, RObject{} }; + } + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp b/ReflectionTemplateLib/rtl/dispatch/hopper_const.h similarity index 76% rename from ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp rename to ReflectionTemplateLib/rtl/dispatch/hopper_const.h index e42ef552..57edc292 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_ctor.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_const.h @@ -12,14 +12,16 @@ #pragma once #include "lambda.h" -#include "RObjectBuilder.hpp" namespace rtl::dispatch { template - template - inline Return lambda::ctor(const lambda_hop&, signature_ts&&...) noexcept + struct hopper_const { - return { error::EmptyRObject, RObject{} }; - } + template + static Return method(const lambda_hop&, signature_ts&&...) noexcept + { + return { error::EmptyRObject, RObject{} }; + } + }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp b/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h similarity index 65% rename from ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp rename to ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h index befceb5a..629f9cd2 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method_nonconst.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h @@ -11,14 +11,24 @@ #pragma once + #include "lambda.h" namespace rtl::dispatch { template - template - inline Return lambda::method_nonconst(const lambda_hop&, signature_ts&&...) noexcept + struct hopper_ctor { - return { error::EmptyRObject, RObject{} }; - } + template + static Return cloner(const lambda_hop&, signature_ts&&...) noexcept + { + return { error::EmptyRObject, RObject{} }; + } + + template + static Return constructor(const lambda_hop&, signature_ts&&...) noexcept + { + return { error::EmptyRObject, RObject{} }; + } + }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_copy_ctor.hpp b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h similarity index 76% rename from ReflectionTemplateLib/rtl/dispatch/lambda_copy_ctor.hpp rename to ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h index 2406fd6e..efdd6ca3 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_copy_ctor.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h @@ -11,16 +11,17 @@ #pragma once - #include "lambda.h" -#include "RObjectBuilder.hpp" namespace rtl::dispatch { template - template - inline Return lambda::copy_ctor(const lambda_hop&, signature_ts&&...) noexcept + struct hopper_nonconst { - return { error::EmptyRObject, RObject{} }; - } + template + static Return method(const lambda_hop&, signature_ts&&...) noexcept + { + return { error::EmptyRObject, RObject{} }; + } + }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index ddde9833..6d95bd2f 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -16,6 +16,12 @@ #include #include "forward_decls.h" + +#include "hopper.h" +#include "hopper_ctor.h" +#include "hopper_const.h" +#include "hopper_nonconst.h" + #include "dispatch_interface.h" namespace rtl::dispatch @@ -23,47 +29,58 @@ namespace rtl::dispatch template struct lambda: public lambda_hop { - using lambda_t = std::function; + using lambda_t = std::function; template static lambda create_ctor(const functor_hop* fptr_hopper) { - std::size_t returnId = detail::TypeId::get(); - return lambda(returnId, fptr_hopper, &ctor); + return lambda(detail::TypeId::get(), fptr_hopper, + &hopper_ctor::template constructor); } template static lambda create_copy_ctor(const functor_hop* fptr_hopper) { - std::size_t returnId = detail::TypeId::get(); - return lambda(returnId, fptr_hopper, ©_ctor); + return lambda(detail::TypeId::get(), fptr_hopper, + &hopper_ctor::template cloner); } template static lambda create_function(const functor_hop* fptr_hopper) { - std::size_t returnId = detail::TypeId::get(); - return lambda(returnId, fptr_hopper, &function); + return lambda(detail::TypeId::get(), fptr_hopper, + &hopper::template function>); } template static lambda create_method_const(const functor_hop* fptr_hopper) { - std::size_t returnId = detail::TypeId::get(); - return lambda(returnId, fptr_hopper, &method_const); + return lambda(detail::TypeId::get(), fptr_hopper, + &hopper_const::template method); } template static lambda create_method_nonconst(const functor_hop* fptr_hopper) { - std::size_t returnId = detail::TypeId::get(); - return lambda(returnId, fptr_hopper, &method_nonconst); + return lambda(detail::TypeId::get(), fptr_hopper, + &hopper_nonconst::template method); } template - decltype(auto) operator()(args_t&&...params) const noexcept + Return operator()(args_t&&...params) const noexcept + { + return m_hopper(*this, std::forward(params)...); + } + + template + decltype(auto) call(args_t&&...params) const noexcept { - return m_hopper(*this, std::forward(params)...); + if constexpr (std::is_same_v) { + hopper::template function(*this, std::forward(params)...); + } + else { + return hopper::template function(*this, std::forward(params)...); + } } private: @@ -86,7 +103,7 @@ namespace rtl::dispatch static Return copy_ctor(const lambda_hop&, signature_ts&&...) noexcept; template - static Return function(const lambda_hop&, signature_ts&&...) noexcept; + static return_t function(const lambda_hop&, signature_ts&&...) noexcept; template static Return method_const(const lambda_hop&, signature_ts&&...) noexcept; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp deleted file mode 100644 index 3a183df9..00000000 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp +++ /dev/null @@ -1,59 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include - -#include "lambda.h" -#include "functor.h" -#include "RObjectBuilder.hpp" - -namespace rtl::dispatch -{ - template - template - inline Return lambda::function(const lambda_hop& hopper, signature_ts&&...params) noexcept - { - auto functor = hopper.functor().get().template get(hopper.m_returnId); - - if constexpr (std::is_same_v) - { - (*functor)(std::forward(params)...); - - return { error::None, RObject{} }; - } - else - { - constexpr bool isConstCastSafe = (!traits::is_const_v); - if constexpr (std::is_reference_v) - { - using T = traits::raw_t; - const T& retObj = functor(std::forward(params)...); - - return { error::None, - detail::RObjectBuilder::template - build(&retObj, std::nullopt, isConstCastSafe) - }; - } - else { - - auto&& retObj = functor(std::forward(params)...); - using T = std::remove_cvref_t; - - return { error::None, - detail::RObjectBuilder::template - build(std::forward(retObj), std::nullopt, isConstCastSafe) - }; - } - } - } -} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp deleted file mode 100644 index 79fa3c5f..00000000 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method_const.hpp +++ /dev/null @@ -1,24 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include "lambda.h" - -namespace rtl::dispatch -{ - template - template - inline Return lambda::method_const(const lambda_hop&, signature_ts&&...) noexcept - { - return { error::EmptyRObject, RObject{} }; - } -} \ No newline at end of file From 599c1cac51a931ce6c4ba7bfac435033b698ed84 Mon Sep 17 00:00:00 2001 From: Neeraj Date: Fri, 19 Sep 2025 10:02:42 +0530 Subject: [PATCH 13/58] Fixed CMakeLists.txt error. --- ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt index 5f1ba12a..cb9634e1 100644 --- a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt @@ -12,7 +12,7 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/hopper.h" "${CMAKE_CURRENT_SOURCE_DIR}/hopper_ctor.h" "${CMAKE_CURRENT_SOURCE_DIR}/hopper_const.h" - "${CMAKE_CURRENT_SOURCE_DIR}/hoppert_nonconst.h" + "${CMAKE_CURRENT_SOURCE_DIR}/hopper_nonconst.h" "${CMAKE_CURRENT_SOURCE_DIR}/CallReflector.h" "${CMAKE_CURRENT_SOURCE_DIR}/FunctionCaller.h" @@ -23,4 +23,4 @@ set(LOCAL_HEADERS ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) -source_group("Header Files\\Dispatch" FILES ${LOCAL_HEADERS}) \ No newline at end of file +source_group("Header Files\\Dispatch" FILES ${LOCAL_HEADERS}) From f401a11e904440004307b7d61a156fd5b3feda95 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Sat, 20 Sep 2025 02:50:13 +0530 Subject: [PATCH 14/58] method-call with known return-type: In Progress. --- RTLBenchmarkApp/CMakeLists.txt | 6 +- .../src/ReflectedCallKnownReturn.cpp | 159 ++++++++++++++++++ ...ectedCall.h => ReflectedCallKnownReturn.h} | 6 +- ...all.cpp => ReflectedCallUnknownReturn.cpp} | 81 +++------ .../src/ReflectedCallUnknownReturn.h | 18 ++ RTLBenchmarkApp/src/StandardCall.cpp | 12 +- RTLBenchmarkApp/src/StandardCall.h | 4 +- RTLBenchmarkApp/src/main.cpp | 24 +-- .../CxxMirrorTests/CxxMirrorObjectTest.cpp | 8 +- .../rtl/builder/FunctorContainer.h | 4 +- .../rtl/builder/SetupConstructor.hpp | 2 +- .../rtl/builder/SetupFunction.hpp | 11 +- .../rtl/builder/SetupMethod.hpp | 24 ++- .../rtl/cache/CMakeLists.txt | 3 +- .../rtl/cache/functor_cache.h | 28 +-- .../rtl/cache/functor_cache_const.h | 26 +-- .../rtl/cache/functor_cache_nonconst.h | 26 +-- .../rtl/cache/lambda_cache.h | 68 -------- .../rtl/cache/lambda_function_cache.h | 59 +++++++ .../rtl/cache/lambda_method_cache.h | 51 ++++++ .../rtl/detail/inc/FunctorId.h | 12 ++ .../rtl/detail/inc/ReflectCast.h | 6 +- .../rtl/detail/inc/forward_decls.h | 21 +++ .../rtl/dispatch/CMakeLists.txt | 5 +- .../rtl/dispatch/CallReflector.h | 12 +- .../rtl/dispatch/FunctionCaller.h | 7 +- .../rtl/dispatch/MethodInvoker.h | 5 +- .../rtl/dispatch/dispatch_interface.h | 53 ++++-- ReflectionTemplateLib/rtl/dispatch/hopper.h | 58 +++---- .../rtl/dispatch/hopper_const.h | 4 +- .../rtl/dispatch/hopper_ctor.h | 12 +- .../rtl/dispatch/hopper_nonconst.h | 62 ++++++- ReflectionTemplateLib/rtl/dispatch/lambda.h | 114 ------------- .../rtl/dispatch/lambda_function.h | 60 +++++++ .../rtl/dispatch/lambda_function.hpp | 46 +++++ .../rtl/dispatch/lambda_method.h | 53 ++++++ .../rtl/dispatch/lambda_method.hpp | 52 ++++++ ReflectionTemplateLib/rtl/inc/Function.h | 2 +- ReflectionTemplateLib/rtl/src/CxxMirror.cpp | 2 +- .../rtl/src/CxxMirrorToJson.cpp | 2 +- 40 files changed, 806 insertions(+), 402 deletions(-) create mode 100644 RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp rename RTLBenchmarkApp/src/{ReflectedCall.h => ReflectedCallKnownReturn.h} (70%) rename RTLBenchmarkApp/src/{ReflectedCall.cpp => ReflectedCallUnknownReturn.cpp} (59%) create mode 100644 RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h delete mode 100644 ReflectionTemplateLib/rtl/cache/lambda_cache.h create mode 100644 ReflectionTemplateLib/rtl/cache/lambda_function_cache.h create mode 100644 ReflectionTemplateLib/rtl/cache/lambda_method_cache.h delete mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda.h create mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_function.h create mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp create mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_method.h create mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp diff --git a/RTLBenchmarkApp/CMakeLists.txt b/RTLBenchmarkApp/CMakeLists.txt index 72cd7492..7e94e053 100644 --- a/RTLBenchmarkApp/CMakeLists.txt +++ b/RTLBenchmarkApp/CMakeLists.txt @@ -41,8 +41,10 @@ add_executable(${CXX_EXE_NAME} src/StandardCall.h src/StandardCall.cpp src/StdFunction.cpp - src/ReflectedCall.h - src/ReflectedCall.cpp + src/ReflectedCallKnownReturn.h + src/ReflectedCallKnownReturn.cpp + src/ReflectedCallUnknownReturn.h + src/ReflectedCallUnknownReturn.cpp ) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp new file mode 100644 index 00000000..9ea401fb --- /dev/null +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -0,0 +1,159 @@ + +#include +#include +#include + +#include "BenchMark.h" +#include "ReflectedCallKnownReturn.h" + + +namespace bm +{ + extern std::optional g_work_done; +} + +namespace cxx +{ + extern const rtl::CxxMirror& mirror(); +} + +namespace +{ + static const rtl::dispatch::lambda* GetMessage_lambda = nullptr; + + static const rtl::dispatch::lambda* SendMessage_lambda = nullptr; + + static const rtl::dispatch::lambda* NodeGetMessage_lambda = nullptr; + + static const rtl::dispatch::lambda* NodeSendMessage_lambda = nullptr; + + static const rtl::RObject nodeObj = []() + { + rtl::Record Node = cxx::mirror().getRecord("Node").value(); + + rtl::Method getMsgNode = Node.getMethod("getMessage").value(); + + rtl::Method sendMsgNode = Node.getMethod("sendMessage").value(); + + rtl::Function getMsg = cxx::mirror().getFunction("getMessage").value(); + + rtl::Function sendMsg = cxx::mirror().getFunction("sendMessage").value(); + + GetMessage_lambda = getMsg.getOverloads()[0].get_lambda_function(); + + SendMessage_lambda = sendMsg.getOverloads()[0].get_lambda_function(); + + NodeGetMessage_lambda = getMsgNode.getOverloads()[0].get_lambda_function(); + + NodeSendMessage_lambda = sendMsgNode.getOverloads()[0].get_lambda_function(); + + auto [err, robj] = Node.create(); + + if (robj.isEmpty()) { + std::cout << "[0] error: " << rtl::to_string(err) << "\n"; + } + + return std::move(robj); + }(); +} + + +namespace +{ + static auto _test0 = []() + { + if( SendMessage_lambda == nullptr || + !SendMessage_lambda->is_returning() || + !SendMessage_lambda->is_signature()) + { + std::cout << "[0] error: signature mismatch.\n"; + return false; + } + return true; + }; + + + static auto _test1 = []() + { + if (NodeSendMessage_lambda == nullptr) + { + std::cout << "[1] error: signature mismatch.\n"; + return false; + } + return true; + }; + + + static auto _test2 = []() + { + if ( GetMessage_lambda == nullptr || + !GetMessage_lambda->is_returning() || + !GetMessage_lambda->is_signature()) + { + std::cout << "[0] error: signature mismatch.\n"; + return false; + } + return true; + }; + + static auto _test3 = []() + { + if (NodeGetMessage_lambda == nullptr) + { + std::cout << "[3] error: signature mismatch.\n"; + return false; + } + return true; + }; +} + + + +void ReflectedCallKnownReturn::set(benchmark::State& state) +{ + static auto passed = _test0(); + for (auto _ : state) + { + if (passed) + { + (*SendMessage_lambda).dispatch(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); + } + } +} + + +void ReflectedCallKnownReturn::get(benchmark::State& state) +{ + static auto passed = _test2(); + for (auto _: state) + { + if (passed) + { + auto retStr = (*GetMessage_lambda).dispatch(bm::g_longStr); + benchmark::DoNotOptimize(retStr); + } + } +} + + +void ReflectedMethodCallKnownReturn::set(benchmark::State& state) +{ + //static auto _=_test1(); + //for (auto _: state) + //{ + // auto error = (NodeSendMessage(nodeObj)(bm::g_longStr).err; + // benchmark::DoNotOptimize(error); + //} +} + + +void ReflectedMethodCallKnownReturn::get(benchmark::State& state) +{ + //static auto _=_test3(); + //for (auto _: state) + //{ + // auto error = NodeGetMessage(nodeObj)(bm::g_longStr).err; + // benchmark::DoNotOptimize(error); + //} +} \ No newline at end of file diff --git a/RTLBenchmarkApp/src/ReflectedCall.h b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h similarity index 70% rename from RTLBenchmarkApp/src/ReflectedCall.h rename to RTLBenchmarkApp/src/ReflectedCallKnownReturn.h index 77b410c5..42a9011f 100644 --- a/RTLBenchmarkApp/src/ReflectedCall.h +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h @@ -2,17 +2,15 @@ #include -struct ReflectedCall +struct ReflectedCallKnownReturn { static void set(benchmark::State& state); static void get(benchmark::State& state); - - static void new_design_set(benchmark::State& state); }; -struct ReflectedMethodCall +struct ReflectedMethodCallKnownReturn { static void set(benchmark::State& state); diff --git a/RTLBenchmarkApp/src/ReflectedCall.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp similarity index 59% rename from RTLBenchmarkApp/src/ReflectedCall.cpp rename to RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index 84cc6370..34f7fb43 100644 --- a/RTLBenchmarkApp/src/ReflectedCall.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -2,16 +2,10 @@ #include #include -#include "ReflectedCall.h" #include "BenchMark.h" +#include "ReflectedCallUnknownReturn.h" - -namespace bm -{ - extern std::optional g_work_done; -} - -namespace cxx +namespace cxx { extern const rtl::CxxMirror& mirror(); } @@ -23,19 +17,19 @@ namespace static rtl::Method NodeGetMessage; static rtl::Method NodeSendMessage; - - static rtl::RObject nodeObj = []() - { + + static rtl::RObject nodeObj = []() + { GetMessage = cxx::mirror().getFunction("getMessage").value(); - + SendMessage = cxx::mirror().getFunction("sendMessage").value(); - auto Node = cxx::mirror().getRecord("Node").value(); + rtl::Record Node = cxx::mirror().getRecord("Node").value(); NodeGetMessage = Node.getMethod("getMessage").value(); - + NodeSendMessage = Node.getMethod("sendMessage").value(); - + auto [err, robj] = Node.create(); if (robj.isEmpty()) { @@ -52,30 +46,16 @@ namespace static auto _test0 = []() { auto err = SendMessage(bm::g_longStr).err; - if (err != rtl::error::None) { - std::cout << "[0] error: "<< rtl::to_string(err)<<"\n"; + std::cout << "[0] error: " << rtl::to_string(err) << "\n"; } return 0; }; - - static auto _test4 = []() - { - auto& hopper = (SendMessage.getFunctors()[0].m_lambda)->get(); - //auto err = hopper(bm::g_longStr).err; - //if (err != rtl::error::None) { - // std::cout << "[4] error: " << rtl::to_string(err) << "\n"; - //} - return hopper; - }; - - static auto _test1 = []() { auto err = NodeSendMessage(nodeObj)(bm::g_longStr).err; - - if (err != rtl::error::None) { + if (err != rtl::error::None) { std::cout << "[1] error: " << rtl::to_string(err) << "\n"; } return 0; @@ -84,7 +64,6 @@ namespace static auto _test2 = []() { auto err = GetMessage(bm::g_longStr).err; - if (err != rtl::error::None) { std::cout << "[2] error: " << rtl::to_string(err) << "\n"; } @@ -94,7 +73,6 @@ namespace static auto _test3 = []() { auto err = NodeGetMessage(nodeObj)(bm::g_longStr).err; - if (err != rtl::error::None) { std::cout << "[3] error: " << rtl::to_string(err) << "\n"; } @@ -104,43 +82,32 @@ namespace -void ReflectedCall::set(benchmark::State& state) +void ReflectedCallUnknownReturn::set(benchmark::State& state) { - static auto _=_test0(); - for (auto _: state) { - + static auto _ = _test0(); + for (auto _ : state) + { auto error = SendMessage(bm::g_longStr).err; benchmark::DoNotOptimize(error); } } -void ReflectedCall::get(benchmark::State& state) +void ReflectedCallUnknownReturn::get(benchmark::State& state) { - static auto _=_test2(); - for (auto _: state) + static auto _ = _test2(); + for (auto _ : state) { auto error = GetMessage(bm::g_longStr).err; benchmark::DoNotOptimize(error); } } -void ReflectedCall::new_design_set(benchmark::State& state) -{ - static const auto& hopper = _test4(); - for (auto _ : state) { - - hopper.call(bm::g_longStr); - //auto ret = hopper(bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done->c_str()); - } -} - -void ReflectedMethodCall::set(benchmark::State& state) +void ReflectedMethodCallUnknownReturn::set(benchmark::State& state) { - static auto _=_test1(); - for (auto _: state) + static auto _ = _test1(); + for (auto _ : state) { auto error = NodeSendMessage(nodeObj)(bm::g_longStr).err; benchmark::DoNotOptimize(error); @@ -148,10 +115,10 @@ void ReflectedMethodCall::set(benchmark::State& state) } -void ReflectedMethodCall::get(benchmark::State& state) +void ReflectedMethodCallUnknownReturn::get(benchmark::State& state) { - static auto _=_test3(); - for (auto _: state) + static auto _ = _test3(); + for (auto _ : state) { auto error = NodeGetMessage(nodeObj)(bm::g_longStr).err; benchmark::DoNotOptimize(error); diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h new file mode 100644 index 00000000..65c28df9 --- /dev/null +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h @@ -0,0 +1,18 @@ +#pragma once + +#include + +struct ReflectedCallUnknownReturn +{ + static void set(benchmark::State& state); + + static void get(benchmark::State& state); +}; + + +struct ReflectedMethodCallUnknownReturn +{ + static void set(benchmark::State& state); + + static void get(benchmark::State& state); +}; \ No newline at end of file diff --git a/RTLBenchmarkApp/src/StandardCall.cpp b/RTLBenchmarkApp/src/StandardCall.cpp index 39dda878..419fd315 100644 --- a/RTLBenchmarkApp/src/StandardCall.cpp +++ b/RTLBenchmarkApp/src/StandardCall.cpp @@ -9,8 +9,8 @@ namespace { static auto _put_line = []() { - std::cout << "-------------------------------------" - "-------------------------------------" << std::endl; + std::cout << "----------------------------------------" + "----------------------------------------" << std::endl; return 0; }; @@ -59,7 +59,7 @@ void NativeCall::get(benchmark::State& state) } -void StdFuncCall::set(benchmark::State& state) +void StdFunctionCall::set(benchmark::State& state) { static auto _=_new_line(); for (auto _: state) @@ -70,7 +70,7 @@ void StdFuncCall::set(benchmark::State& state) } -void StdFuncMethodCall::set(benchmark::State& state) +void StdFunctionMethodCall::set(benchmark::State& state) { static auto _=_new_line(); for (auto _: state) @@ -81,7 +81,7 @@ void StdFuncMethodCall::set(benchmark::State& state) } -void StdFuncCall::get(benchmark::State& state) +void StdFunctionCall::get(benchmark::State& state) { static auto _=_new_line(); for (auto _: state) @@ -91,7 +91,7 @@ void StdFuncCall::get(benchmark::State& state) } -void StdFuncMethodCall::get(benchmark::State& state) +void StdFunctionMethodCall::get(benchmark::State& state) { static auto _=_new_line(); for (auto _: state) diff --git a/RTLBenchmarkApp/src/StandardCall.h b/RTLBenchmarkApp/src/StandardCall.h index da2e4a45..76bd70f2 100644 --- a/RTLBenchmarkApp/src/StandardCall.h +++ b/RTLBenchmarkApp/src/StandardCall.h @@ -10,7 +10,7 @@ struct NativeCall }; -struct StdFuncCall +struct StdFunctionCall { static void set(benchmark::State& state); @@ -18,7 +18,7 @@ struct StdFuncCall }; -struct StdFuncMethodCall +struct StdFunctionMethodCall { static void set(benchmark::State& state); diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index e2de9214..77914b8a 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -4,24 +4,28 @@ #include #include "StandardCall.h" -#include "ReflectedCall.h" +#include "ReflectedCallKnownReturn.h" +#include "ReflectedCallUnknownReturn.h" BENCHMARK(NativeCall::set); -BENCHMARK(StdFuncCall::set); -BENCHMARK(ReflectedCall::new_design_set); -BENCHMARK(ReflectedCall::set); +BENCHMARK(StdFunctionCall::set); +BENCHMARK(ReflectedCallKnownReturn::set); +BENCHMARK(ReflectedCallUnknownReturn::set); -BENCHMARK(StdFuncMethodCall::set); -BENCHMARK(ReflectedMethodCall::set); +BENCHMARK(StdFunctionMethodCall::set); +//BENCHMARK(ReflectedMethodCallKnownReturn::set); +BENCHMARK(ReflectedMethodCallUnknownReturn::set); BENCHMARK(NativeCall::get); -BENCHMARK(StdFuncCall::get); -BENCHMARK(ReflectedCall::get); +BENCHMARK(StdFunctionCall::get); +BENCHMARK(ReflectedCallKnownReturn::get); +BENCHMARK(ReflectedCallUnknownReturn::get); -BENCHMARK(StdFuncMethodCall::get); -BENCHMARK(ReflectedMethodCall::get); +BENCHMARK(StdFunctionMethodCall::get); +//BENCHMARK(ReflectedMethodCallKnownReturn::get); +BENCHMARK(ReflectedMethodCallUnknownReturn::get); namespace bm { diff --git a/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp b/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp index d6f62f6e..41492567 100644 --- a/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp +++ b/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp @@ -287,8 +287,8 @@ namespace rtl_tests // Even though the functions are registered in different namespaces, // the underlying FunctorIds (which identify function-pointers) must be equal. - const std::vector& cfunctorIds = cstrLen->getFunctors(); - const std::vector& stdfunctorIds = stdStrLen->getFunctors(); + const std::vector& cfunctorIds = cstrLen->getOverloads(); + const std::vector& stdfunctorIds = stdStrLen->getOverloads(); EXPECT_EQ(cfunctorIds, stdfunctorIds); } @@ -349,8 +349,8 @@ namespace rtl_tests // Despite different symbolic names, both reflect the same function-pointer. // Hence, their FunctorIds must be identical. - const std::vector& cfunctorIds = cstrLen->getFunctors(); - const std::vector& stdfunctorIds = stdStrLen->getFunctors(); + const std::vector& cfunctorIds = cstrLen->getOverloads(); + const std::vector& stdfunctorIds = stdStrLen->getOverloads(); EXPECT_EQ(cfunctorIds, stdfunctorIds); } diff --git a/ReflectionTemplateLib/rtl/builder/FunctorContainer.h b/ReflectionTemplateLib/rtl/builder/FunctorContainer.h index 2ecfbf4c..532fa188 100644 --- a/ReflectionTemplateLib/rtl/builder/FunctorContainer.h +++ b/ReflectionTemplateLib/rtl/builder/FunctorContainer.h @@ -15,7 +15,7 @@ #include #include -#include "lambda_cache.h" +#include "lambda_function_cache.h" #include "rtl_constants.h" #include "CallReflector.h" #include "SetupFunction.h" @@ -47,7 +47,7 @@ namespace rtl { } //get the vector holding lambdas as 'const-ref' - FORCE_INLINE const static std::vector& getFunctors() { + FORCE_INLINE const static std::vector& getOverloads() { static std::vector& functorTable = getFunctorTable(); return functorTable; } diff --git a/ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp b/ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp index bfa6a1cd..dfe8245e 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupConstructor.hpp @@ -175,7 +175,7 @@ namespace rtl::detail return (itr != ctorSet.end() ? itr->second : index_none); }; - //auto& lambdaCache = lambda_cache::get<_signature...>(); + //auto& lambdaCache = lambda_function::get<_signature...>(); //const auto& pushLambdaHopper = [&]()-> std::size_t //{ // return lambdaCache.push_cloner<_recordType>(); diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index ac0cc135..5be59247 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -13,8 +13,9 @@ #include -#include "lambda_cache.h" #include "functor_cache.h" +#include "lambda_function.hpp" +#include "lambda_function_cache.h" #include "SetupFunction.h" #include "RObjectBuilder.hpp" @@ -93,16 +94,16 @@ namespace rtl const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = dispatch::lambda_cache<_signature...>::instance(); - auto& functorCache = dispatch::functor_cache<_signature...>::instance(); + auto& lambdaCache = cache::lambda_function<_signature...>::instance(); + auto& functorCache = cache::function_ptr<_signature...>::instance(); auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambda = lambdaCache.template push_function<_returnType>(functor); + auto& lambda = lambdaCache.template push<_returnType>(functor); lambdaPtr = λ }; const auto& getIndex = [&]()-> std::size_t { - auto& functorCache = dispatch::functor_cache<_signature...>::instance(); + auto& functorCache = cache::function_ptr<_signature...>::instance(); auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); if (lambdaIndex != rtl::index_none) { lambdaPtr = functor->m_lambda; diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index f420f873..d2ecf3d7 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -21,6 +21,10 @@ #include "functor_cache_const.h" #include "functor_cache_nonconst.h" +#include "lambda_method.hpp" +#include "lambda_method_cache.h" + + namespace rtl::detail { template @@ -164,17 +168,20 @@ namespace rtl::detail const dispatch::lambda_hop* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = dispatch::lambda_cache<_signature...>::instance(); - auto& functorCache = dispatch::functor_cache_nonconst<_recordType, _signature...>::instance(); + auto& lambdaCache = cache::lambda_method<_recordType, _signature...>::instance(); + auto& functorCache = cache::method_ptr<_recordType, _signature...>::instance(); + auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambda = lambdaCache.template push_method_nonconst<_recordType, _returnType>(functor); + auto& lambda = lambdaCache.template push<_recordType, _returnType>(functor); + lambdaPtr = λ }; const auto& getIndex = [&]()-> std::size_t { - auto& functorCache = dispatch::functor_cache_nonconst<_recordType, _signature...>::instance(); + auto& functorCache = cache::method_ptr<_recordType, _signature...>::instance(); auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); + if (lambdaIndex != rtl::index_none) { lambdaPtr = functor->m_lambda; } @@ -232,17 +239,20 @@ namespace rtl::detail const dispatch::lambda_hop* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = dispatch::lambda_cache<_signature...>::instance(); - auto& functorCache = dispatch::functor_cache_const<_recordType, _signature...>::instance(); + auto& lambdaCache = cache::lambda_function<_signature...>::instance(); + auto& functorCache = cache::const_method_ptr<_recordType, _signature...>::instance(); + auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); auto& lambda = lambdaCache.template push_method_const<_recordType, _returnType>(functor); + lambdaPtr = λ }; const auto& getIndex = [&]()-> std::size_t { - auto& functorCache = dispatch::functor_cache_const<_recordType, _signature...>::instance(); + auto& functorCache = cache::const_method_ptr<_recordType, _signature...>::instance(); auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); + if (lambdaIndex != rtl::index_none) { lambdaPtr = functor->m_lambda; } diff --git a/ReflectionTemplateLib/rtl/cache/CMakeLists.txt b/ReflectionTemplateLib/rtl/cache/CMakeLists.txt index bd77a74f..e31be8d4 100644 --- a/ReflectionTemplateLib/rtl/cache/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/cache/CMakeLists.txt @@ -2,7 +2,8 @@ # Collect headers (absolute paths) set(LOCAL_HEADERS - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_cache.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method_cache.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function_cache.h" "${CMAKE_CURRENT_SOURCE_DIR}/functor_cache.h" "${CMAKE_CURRENT_SOURCE_DIR}/functor_cache_const.h" "${CMAKE_CURRENT_SOURCE_DIR}/functor_cache_nonconst.h" diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache.h b/ReflectionTemplateLib/rtl/cache/functor_cache.h index 4ba654a8..484ee6e0 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache.h +++ b/ReflectionTemplateLib/rtl/cache/functor_cache.h @@ -15,23 +15,23 @@ #include "functor.h" -namespace rtl::dispatch +namespace rtl::cache { template - struct functor_cache + struct function_ptr { - using functor_t = functor; + using functor_t = dispatch::functor; - static const functor_cache& instance() + static const function_ptr& instance() { - static functor_cache instance_; + static function_ptr instance_; return instance_; } template - const functor_hop* push(return_t(*fptr)(signature_ts...), std::size_t lambda_index) const + const dispatch::functor_hop* push(return_t(*fptr)(signature_ts...), std::size_t lambda_index) const { - using voidfn_t = typename functor::voidfn_t; + using voidfn_t = typename dispatch::functor::voidfn_t; auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); m_cache.emplace_back(std::make_pair(functor , lambda_index)); @@ -39,7 +39,7 @@ namespace rtl::dispatch } template - std::pair find(return_t(*fptr)(signature_ts...)) const + std::pair find(return_t(*fptr)(signature_ts...)) const { for (auto& itr : m_cache) { @@ -51,16 +51,16 @@ namespace rtl::dispatch return { nullptr, rtl::index_none }; } - functor_cache(functor_cache&&) = delete; - functor_cache(const functor_cache&) = delete; - functor_cache& operator=(functor_cache&&) = delete; - functor_cache& operator=(const functor_cache&) = delete; + function_ptr(function_ptr&&) = delete; + function_ptr(const function_ptr&) = delete; + function_ptr& operator=(function_ptr&&) = delete; + function_ptr& operator=(const function_ptr&) = delete; private: // No reallocation occurs; original objects stay intact - mutable std::list> m_cache; + mutable std::list> m_cache; - functor_cache() {} + function_ptr() {} }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_const.h b/ReflectionTemplateLib/rtl/cache/functor_cache_const.h index a7a351a3..c1775fce 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache_const.h +++ b/ReflectionTemplateLib/rtl/cache/functor_cache_const.h @@ -15,23 +15,23 @@ #include "functor_const.h" -namespace rtl::dispatch +namespace rtl::cache { template - struct functor_cache_const + struct const_method_ptr { - using functor_t = functor_const; + using functor_t = dispatch::functor_const; - static const functor_cache_const& instance() + static const const_method_ptr& instance() { - static functor_cache_const instance_; + static const_method_ptr instance_; return instance_; } template - const functor_hop* push(return_t(record_t::* fptr)(signature_ts...) const, std::size_t lambda_index) const + const dispatch::functor_hop* push(return_t(record_t::* fptr)(signature_ts...) const, std::size_t lambda_index) const { - using voidfn_t = typename functor_const::voidfn_t; + using voidfn_t = typename dispatch::functor_const::voidfn_t; auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); m_cache.emplace_back(std::make_pair(functor, lambda_index)); return &(m_cache.back().first); @@ -39,7 +39,7 @@ namespace rtl::dispatch } template - std::pair find(return_t(record_t::* fptr)(signature_ts...) const) const + std::pair find(return_t(record_t::* fptr)(signature_ts...) const) const { for (auto& itr : m_cache) { @@ -51,16 +51,16 @@ namespace rtl::dispatch return { nullptr, rtl::index_none }; } - functor_cache_const(functor_cache_const&&) = delete; - functor_cache_const(const functor_cache_const&) = delete; - functor_cache_const& operator=(functor_cache_const&&) = delete; - functor_cache_const& operator=(const functor_cache_const&) = delete; + const_method_ptr(const_method_ptr&&) = delete; + const_method_ptr(const const_method_ptr&) = delete; + const_method_ptr& operator=(const_method_ptr&&) = delete; + const_method_ptr& operator=(const const_method_ptr&) = delete; private: // No reallocation occurs; original objects stay intact mutable std::list> m_cache; - functor_cache_const() {} + const_method_ptr() {} }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h b/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h index e9a240e9..41e67629 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h +++ b/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h @@ -15,30 +15,30 @@ #include "functor_nonconst.h" -namespace rtl::dispatch +namespace rtl::cache { template - struct functor_cache_nonconst + struct method_ptr { - using functor_t = functor_nonconst; + using functor_t = dispatch::functor_nonconst; - static const functor_cache_nonconst& instance() + static const method_ptr& instance() { - static const functor_cache_nonconst instance_; + static const method_ptr instance_; return instance_; } template - const functor_hop* push(return_t(record_t::* fptr)(signature_ts...), std::size_t lambda_index) const + const dispatch::functor_hop* push(return_t(record_t::* fptr)(signature_ts...), std::size_t lambda_index) const { - using voidfn_t = typename functor_nonconst::voidfn_t; + using voidfn_t = typename dispatch::functor_nonconst::voidfn_t; auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); m_cache.emplace_back(std::make_pair(functor, lambda_index)); return &(m_cache.back().first); } template - std::pair find(return_t(record_t::* fptr)(signature_ts...)) const + std::pair find(return_t(record_t::* fptr)(signature_ts...)) const { for (auto& itr : m_cache) { @@ -50,16 +50,16 @@ namespace rtl::dispatch return { nullptr, rtl::index_none }; } - functor_cache_nonconst(functor_cache_nonconst&&) = delete; - functor_cache_nonconst(const functor_cache_nonconst&) = delete; - functor_cache_nonconst& operator=(functor_cache_nonconst&&) = delete; - functor_cache_nonconst& operator=(const functor_cache_nonconst&) = delete; + method_ptr(method_ptr&&) = delete; + method_ptr(const method_ptr&) = delete; + method_ptr& operator=(method_ptr&&) = delete; + method_ptr& operator=(const method_ptr&) = delete; private: // No reallocation occurs; original objects stay intact mutable std::list> m_cache; - functor_cache_nonconst() {} + method_ptr() {} }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/lambda_cache.h b/ReflectionTemplateLib/rtl/cache/lambda_cache.h deleted file mode 100644 index 21d249f1..00000000 --- a/ReflectionTemplateLib/rtl/cache/lambda_cache.h +++ /dev/null @@ -1,68 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include - -#include "lambda.h" - -namespace rtl::dispatch -{ - template - struct lambda_cache - { - static lambda_cache& instance() - { - static lambda_cache instance_; - return instance_; - } - - template - const lambda& push_function(const functor_hop* fptr_hopper) - { - m_cache.push_back(lambda::template create_function(fptr_hopper)); - const lambda& lambda_hop = m_cache.back(); - fptr_hopper->set_lambda(&lambda_hop); - return lambda_hop; - } - - template - const lambda& push_method_const(const functor_hop* fptr_hopper) - { - m_cache.push_back(lambda::template create_method_const(fptr_hopper)); - const lambda& lambda_hop = m_cache.back(); - fptr_hopper->set_lambda(&lambda_hop); - return lambda_hop; - } - - template - const lambda& push_method_nonconst(const functor_hop* fptr_hopper) - { - m_cache.push_back(lambda::template create_method_nonconst(fptr_hopper)); - const lambda& lambda_hop = m_cache.back(); - fptr_hopper->set_lambda(&lambda_hop); - return lambda_hop; - } - - lambda_cache(lambda_cache&&) = delete; - lambda_cache(const lambda_cache&) = delete; - lambda_cache& operator=(lambda_cache&&) = delete; - lambda_cache& operator=(const lambda_cache&) = delete; - - private: - - // No reallocation occurs; original objects stay intact - std::list> m_cache; - - lambda_cache() {} - }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/lambda_function_cache.h b/ReflectionTemplateLib/rtl/cache/lambda_function_cache.h new file mode 100644 index 00000000..fae533a3 --- /dev/null +++ b/ReflectionTemplateLib/rtl/cache/lambda_function_cache.h @@ -0,0 +1,59 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "lambda_function.h" + +namespace rtl::cache +{ + template + struct lambda_function + { + static const lambda_function& instance() + { + static const lambda_function instance_; + return instance_; + } + + template + const dispatch::lambda& push(const dispatch::functor_hop* fptr_hopper) const + { + m_cache.push_back(dispatch::lambda::template create(fptr_hopper)); + const dispatch::lambda& lambda_hop = m_cache.back(); + fptr_hopper->set_lambda(&lambda_hop); + return lambda_hop; + } + + template + const dispatch::lambda& push_method_const(const dispatch::functor_hop* fptr_hopper) const + { + m_cache.push_back(dispatch::lambda::template create_method_const(fptr_hopper)); + const dispatch::lambda& lambda_hop = m_cache.back(); + fptr_hopper->set_lambda(&lambda_hop); + return lambda_hop; + } + + lambda_function(lambda_function&&) = delete; + lambda_function(const lambda_function&) = delete; + lambda_function& operator=(lambda_function&&) = delete; + lambda_function& operator=(const lambda_function&) = delete; + + private: + + // No reallocation occurs; original objects stay intact + mutable std::list> m_cache; + + lambda_function() {} + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/lambda_method_cache.h b/ReflectionTemplateLib/rtl/cache/lambda_method_cache.h new file mode 100644 index 00000000..a43268ed --- /dev/null +++ b/ReflectionTemplateLib/rtl/cache/lambda_method_cache.h @@ -0,0 +1,51 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "lambda_function.h" + + +namespace rtl::cache +{ + template + struct lambda_method + { + static const lambda_method& instance() + { + static const lambda_method instance_; + return instance_; + } + + template + const dispatch::lambda_method& push(const dispatch::functor_hop* fptr_hopper) const + { + m_cache.push_back(dispatch::lambda_method::template create(fptr_hopper)); + const dispatch::lambda_method& lambda_hop = m_cache.back(); + fptr_hopper->set_lambda(&lambda_hop); + return lambda_hop; + } + + lambda_method(lambda_method&&) = delete; + lambda_method(const lambda_method&) = delete; + lambda_method& operator=(lambda_method&&) = delete; + lambda_method& operator=(const lambda_method&) = delete; + + private: + + // No reallocation occurs; original objects stay intact + mutable std::list> m_cache; + + lambda_method() {} + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index 788827bb..6514cfc2 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -14,6 +14,8 @@ #include "rtl_typeid.h" #include "rtl_constants.h" #include "forward_decls.h" +#include "lambda_method.h" +#include "lambda_function.h" namespace rtl::detail { @@ -49,6 +51,16 @@ namespace rtl::detail GETTER(std::size_t, SignatureId, m_containerId) GETTER(std::string, SignatureStr, m_signature) + template + const dispatch::lambda<_signature...>* get_lambda_function() const { + return m_lambda->get_function<_signature...>(); + } + + template + const dispatch::lambda_method<_signature...>* get_lambda_method() const { + return m_lambda->get_method(); + } + /* @method: getHashCode() @return: std::size_t (a unique hash-code for a functor) * 'm_containerId' will be same for functors(non-member) with same signatures. diff --git a/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h b/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h index ae748ba8..1e3fc638 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h +++ b/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h @@ -16,11 +16,7 @@ #include #include "rtl_traits.h" - -namespace rtl { - - class CxxMirror; -} +#include "forward_decls.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index 46404cb9..0e1776b9 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -19,6 +19,12 @@ namespace rtl class RObject; + class Function; + + class Method; + + class CxxMirror; + namespace detail { struct FunctorId; @@ -32,5 +38,20 @@ namespace rtl struct lambda_hop; struct functor_hop; + + template + class lambda; + + template + class lambda_method; + + template + struct functor; + + template + struct functor_const; + + template + struct functor_nonconst; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt index cb9634e1..45ffd2a7 100644 --- a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt @@ -8,7 +8,10 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/functor_const.h" "${CMAKE_CURRENT_SOURCE_DIR}/functor_nonconst.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function.hpp" "${CMAKE_CURRENT_SOURCE_DIR}/hopper.h" "${CMAKE_CURRENT_SOURCE_DIR}/hopper_ctor.h" "${CMAKE_CURRENT_SOURCE_DIR}/hopper_const.h" diff --git a/ReflectionTemplateLib/rtl/dispatch/CallReflector.h b/ReflectionTemplateLib/rtl/dispatch/CallReflector.h index 4940eb8f..775b6786 100644 --- a/ReflectionTemplateLib/rtl/dispatch/CallReflector.h +++ b/ReflectionTemplateLib/rtl/dispatch/CallReflector.h @@ -33,8 +33,8 @@ namespace rtl::detail { */ template FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, _params&&..._args) { - //'getFunctors()' must be implemented by _derivedType (FunctorContainer). - return _derivedType::getFunctors()[pFunctorId.m_lambdaIndex](pFunctorId, std::forward<_params>(_args)...); + //'getOverloads()' must be implemented by _derivedType (FunctorContainer). + return _derivedType::getOverloads()[pFunctorId.m_lambdaIndex](pFunctorId, std::forward<_params>(_args)...); } @@ -45,16 +45,16 @@ namespace rtl::detail { */ template FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, rtl::alloc pAllocType, const detail::FunctorId& pClonerId, _params&&..._args) { - //'getFunctors()' must be implemented by _derivedType (FunctorContainer). - return _derivedType::getFunctors()[pFunctorId.m_lambdaIndex](pFunctorId, pAllocType, pClonerId, std::forward<_params>(_args)...); + //'getOverloads()' must be implemented by _derivedType (FunctorContainer). + return _derivedType::getOverloads()[pFunctorId.m_lambdaIndex](pFunctorId, pAllocType, pClonerId, std::forward<_params>(_args)...); } template FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, const RObject& pSrcObj, rtl::alloc pAllocType) { - //'getFunctors()' must be implemented by _derivedType (FunctorContainer). - return _derivedType::getFunctors()[pFunctorId.m_lambdaIndex](pFunctorId, pSrcObj, pAllocType); + //'getOverloads()' must be implemented by _derivedType (FunctorContainer). + return _derivedType::getOverloads()[pFunctorId.m_lambdaIndex](pFunctorId, pSrcObj, pAllocType); } diff --git a/ReflectionTemplateLib/rtl/dispatch/FunctionCaller.h b/ReflectionTemplateLib/rtl/dispatch/FunctionCaller.h index fdcfb53b..ae63d80a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/FunctionCaller.h +++ b/ReflectionTemplateLib/rtl/dispatch/FunctionCaller.h @@ -11,12 +11,9 @@ #pragma once -#include "RObject.h" +#include "forward_decls.h" -namespace rtl -{ - class Function; -} +#include "RObject.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/dispatch/MethodInvoker.h b/ReflectionTemplateLib/rtl/dispatch/MethodInvoker.h index 198cf761..4cbb83fe 100644 --- a/ReflectionTemplateLib/rtl/dispatch/MethodInvoker.h +++ b/ReflectionTemplateLib/rtl/dispatch/MethodInvoker.h @@ -11,11 +11,8 @@ #pragma once -namespace rtl { +#include "forward_decls.h" - //forward decls - class Method; -} namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h b/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h index eee70c23..6c720eb0 100644 --- a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h +++ b/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h @@ -19,11 +19,6 @@ namespace rtl::dispatch { - struct functor_hop; - - template - struct lambda; - struct lambda_hop { const functor_hop& functor() const @@ -31,15 +26,50 @@ namespace rtl::dispatch return *m_functor; } + template + bool is_member() const + { + return (m_recordId == detail::TypeId>::get() || + m_recordId == detail::TypeId>::get()); + } + + template + bool is_returning() const + { + return (m_returnId == detail::TypeId::get()); + } + + template + bool is_signature() const + { + return (m_signatureId == detail::TypeId>::get()); + } + template - const lambda& get() const + const lambda* get_function() const { - return (*static_cast*>(this)); + std::size_t typeId = detail::TypeId>::get(); + if (typeId == m_signatureId) { + return static_cast*>(this); + } + return nullptr; + } + + template + const lambda_method* get_method() const + { + std::size_t recordId = detail::TypeId::get(); + std::size_t typeId = detail::TypeId>::get(); + if (typeId == m_signatureId && recordId == m_recordId) { + return static_cast*>(this); + } + return nullptr; } // protected: const functor_hop* m_functor = nullptr; + std::size_t m_recordId = detail::TypeId<>::None; std::size_t m_returnId = detail::TypeId<>::None; std::size_t m_signatureId = detail::TypeId<>::None; std::vector m_argumentsId = {}; @@ -49,15 +79,6 @@ namespace rtl::dispatch namespace rtl::dispatch { - template - struct functor; - - template - struct functor_const; - - template - struct functor_nonconst; - struct functor_hop { void set_lambda(const lambda_hop* lambda) const diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper.h b/ReflectionTemplateLib/rtl/dispatch/hopper.h index 62a26bbb..11451ff9 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper.h @@ -13,7 +13,7 @@ #include -#include "lambda.h" +#include "lambda_function.h" #include "functor.h" //#include "RObjectBuilder.hpp" @@ -22,59 +22,59 @@ namespace rtl::dispatch template struct hopper { - template - static decltype(auto) function(const lambda_hop& lambda_ref, signature_ts&&...params) noexcept + template requires (std::is_same_v == false) + static decltype(auto) dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept { - auto functor = lambda_ref.functor().template get().template get(lambda_ref.m_returnId); + auto functor = lambda_ref.functor().template get() + .template get(lambda_ref.m_returnId); + if constexpr (std::is_same_v) { - (*functor)(std::forward(params)...); + (*functor)(params...); } else { - return (*functor)(std::forward(params)...); + return (*functor)(params...); } } - template requires (is_void_t == true) - static Return function(const lambda_hop& lambda_ref, signature_ts&&...params) noexcept + + template requires (void_t == true) + static Return dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept { - if constexpr (std::is_same_v) { - auto functor = lambda_ref.functor().template get().template get(lambda_ref.m_returnId); - (*functor)(std::forward(params)...); + if constexpr (std::is_same_v) + { + auto functor = lambda_ref.functor().template get() + .template get(lambda_ref.m_returnId); + + (*functor)(params...); } - else { + else + { static_assert("return-type mismatch."); } return { error::None, RObject{} }; } - template requires (is_void_t == false) - static Return function(const lambda_hop& lambda_ref, signature_ts&&...params) noexcept + + template requires (void_t == false) + static Return dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept { constexpr bool isConstCastSafe = (!traits::is_const_v); - auto functor = lambda_ref.functor().template get().template get(lambda_ref.m_returnId); + auto functor = lambda_ref.functor().template get() + .template get(lambda_ref.m_returnId); if constexpr (std::is_reference_v) { using T = traits::raw_t; - const T& retObj = functor(std::forward(params)...); - - //return { error::None, - // detail::RObjectBuilder::template - // build(&retObj, std::nullopt, isConstCastSafe) - //}; + const T& retObj = (*functor)(params...); + return { error::None, RObject{} }; } else { - auto&& retObj = functor(std::forward(params)...); - using T = std::remove_cvref_t; - - //return { error::None, - // detail::RObjectBuilder::template - // build(std::forward(retObj), std::nullopt, isConstCastSafe) - //}; + //auto&& retObj = (*functor)(params...); + //using T = std::remove_cvref_t; + return { error::None, RObject{} }; } - return { error::None, RObject{} }; } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_const.h b/ReflectionTemplateLib/rtl/dispatch/hopper_const.h index 57edc292..00acfdc4 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_const.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_const.h @@ -11,7 +11,7 @@ #pragma once -#include "lambda.h" +#include "lambda_function.h" namespace rtl::dispatch { @@ -19,7 +19,7 @@ namespace rtl::dispatch struct hopper_const { template - static Return method(const lambda_hop&, signature_ts&&...) noexcept + static Return dispatch(const lambda_hop&, const signature_ts&...) noexcept { return { error::EmptyRObject, RObject{} }; } diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h b/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h index 629f9cd2..076e6cb9 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h @@ -12,7 +12,7 @@ #pragma once -#include "lambda.h" +#include "lambda_function.h" namespace rtl::dispatch { @@ -20,15 +20,21 @@ namespace rtl::dispatch struct hopper_ctor { template - static Return cloner(const lambda_hop&, signature_ts&&...) noexcept + static Return dispatch(const lambda_hop&, const signature_ts&...) noexcept { return { error::EmptyRObject, RObject{} }; } + }; + + template + struct hopper_copyctor + { template - static Return constructor(const lambda_hop&, signature_ts&&...) noexcept + static Return dispatch(const lambda_hop&, signature_ts&&...) noexcept { return { error::EmptyRObject, RObject{} }; } }; + } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h index efdd6ca3..e629ad66 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h @@ -11,17 +11,69 @@ #pragma once -#include "lambda.h" +#include "forward_decls.h" + +#include "lambda_function.h" +#include "functor.h" namespace rtl::dispatch { - template + template struct hopper_nonconst { - template - static Return method(const lambda_hop&, signature_ts&&...) noexcept + template requires (std::is_same_v == false) + static decltype(auto) dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept + { + auto functor = lambda_ref.functor().template get_nonconst() + .template get(lambda_ref.m_returnId); + + if constexpr (std::is_same_v) { + (target.*functor)(params...); + } + else { + return (target.*functor)(params...); + } + } + + + template requires (void_t == true) + static Return dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept + { + if constexpr (std::is_same_v) + { + auto functor = lambda_ref.functor().template get_nonconst() + .template get(lambda_ref.m_returnId); + + (target.*functor)(params...); + } + else + { + static_assert("return-type mismatch."); + } + return { error::None, RObject{} }; + } + + + template requires (void_t == false) + static Return dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept { - return { error::EmptyRObject, RObject{} }; + constexpr bool isConstCastSafe = (!traits::is_const_v); + + auto functor = lambda_ref.functor().template get_nonconst() + .template get(lambda_ref.m_returnId); + + if constexpr (std::is_reference_v) + { + using T = traits::raw_t; + const T& retObj = (target.*functor)(params...); + return { error::None, RObject{} }; + } + else { + + auto&& retObj = (target.*functor)(params...); + using T = std::remove_cvref_t; + return { error::None, RObject{} }; + } } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h deleted file mode 100644 index 6d95bd2f..00000000 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ /dev/null @@ -1,114 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include -#include -#include - -#include "forward_decls.h" - -#include "hopper.h" -#include "hopper_ctor.h" -#include "hopper_const.h" -#include "hopper_nonconst.h" - -#include "dispatch_interface.h" - -namespace rtl::dispatch -{ - template - struct lambda: public lambda_hop - { - using lambda_t = std::function; - - template - static lambda create_ctor(const functor_hop* fptr_hopper) - { - return lambda(detail::TypeId::get(), fptr_hopper, - &hopper_ctor::template constructor); - } - - template - static lambda create_copy_ctor(const functor_hop* fptr_hopper) - { - return lambda(detail::TypeId::get(), fptr_hopper, - &hopper_ctor::template cloner); - } - - template - static lambda create_function(const functor_hop* fptr_hopper) - { - return lambda(detail::TypeId::get(), fptr_hopper, - &hopper::template function>); - } - - template - static lambda create_method_const(const functor_hop* fptr_hopper) - { - return lambda(detail::TypeId::get(), fptr_hopper, - &hopper_const::template method); - } - - template - static lambda create_method_nonconst(const functor_hop* fptr_hopper) - { - return lambda(detail::TypeId::get(), fptr_hopper, - &hopper_nonconst::template method); - } - - template - Return operator()(args_t&&...params) const noexcept - { - return m_hopper(*this, std::forward(params)...); - } - - template - decltype(auto) call(args_t&&...params) const noexcept - { - if constexpr (std::is_same_v) { - hopper::template function(*this, std::forward(params)...); - } - else { - return hopper::template function(*this, std::forward(params)...); - } - } - - private: - - const lambda_t m_hopper; - - lambda(std::size_t returnId, const functor_hop* functor, lambda_t hopper) noexcept - : m_hopper(std::move(hopper)) - { - m_functor = functor; - m_returnId = returnId; - m_signatureId = detail::TypeId>::get(); - detail::TypeId::get(m_argumentsId); - } - - template - static Return ctor(const lambda_hop&, signature_ts&&...) noexcept; - - template - static Return copy_ctor(const lambda_hop&, signature_ts&&...) noexcept; - - template - static return_t function(const lambda_hop&, signature_ts&&...) noexcept; - - template - static Return method_const(const lambda_hop&, signature_ts&&...) noexcept; - - template - static Return method_nonconst(const lambda_hop&, signature_ts&&...) noexcept; - }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h new file mode 100644 index 00000000..8ff7d4aa --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -0,0 +1,60 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include +#include +#include + +#include "forward_decls.h" + +#include "hopper.h" +#include "hopper_ctor.h" +#include "hopper_const.h" +#include "dispatch_interface.h" + +namespace rtl::dispatch +{ + template + class lambda: public lambda_hop + { + using lambda_t = std::function; + + const lambda_t m_hopper; + + lambda(std::size_t returnId, const functor_hop* functor, lambda_t hopper) noexcept + : m_hopper(std::move(hopper)) + { + m_functor = functor; + m_returnId = returnId; + m_signatureId = detail::TypeId>::get(); + detail::TypeId::get(m_argumentsId); + } + + public: + + decltype(auto) operator()(const signature_ts&...) const noexcept; + + template + decltype(auto) dispatch(const signature_ts&...) const noexcept; + + template + static lambda create(const functor_hop*); + + template + static lambda create_method_const(const functor_hop* fptr_hopper) + { + return lambda(detail::TypeId::get(), fptr_hopper, + &hopper_const::template dispatch); + } + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp new file mode 100644 index 00000000..b959eb1a --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp @@ -0,0 +1,46 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "lambda_function.h" + +namespace rtl::dispatch +{ + template + template + static lambda lambda::create(const functor_hop* fptr_hopper) + { + return lambda(detail::TypeId::get(), fptr_hopper, + &hopper::template dispatch, return_t>); + } + + template + inline decltype(auto) lambda::operator()(const signature_ts& ...params) const noexcept + { + //TODO: static-assert signature_ts == args_t. + return m_hopper(*this, params...); + } + + + template + template + inline decltype(auto) lambda::dispatch(const signature_ts&...params) const noexcept + { + //TODO: static-assert signature_ts == args_t. + if constexpr (std::is_same_v) { + hopper::template dispatch(*this, params...); + } + else { + return hopper::template dispatch(*this, params...); + } + } +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h new file mode 100644 index 00000000..9cf7c1d9 --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -0,0 +1,53 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "forward_decls.h" +#include "dispatch_interface.h" +#include "hopper_nonconst.h" + +namespace rtl::dispatch +{ + template + class lambda_method : public lambda_hop + { + using lambda_t = std::function; + + const lambda_t m_hopper; + + lambda_method(std::size_t returnId, const functor_hop* functor, lambda_t hopper) noexcept + : m_hopper(std::move(hopper)) + { + m_functor = functor; + m_returnId = returnId; + m_recordId = detail::TypeId::get(); + m_signatureId = detail::TypeId>::get(); + detail::TypeId::get(m_argumentsId); + } + + public: + + template + static lambda_method create(const functor_hop* fptr_hopper) + { + return lambda_method(detail::TypeId::get(), fptr_hopper, nullptr); + //&hopper_nonconst::template dispatch, return_t>); + } + + decltype(auto) operator()(record_t&, const signature_ts&...) const noexcept; + + template + decltype(auto) dispatch(record_t&, const signature_ts&...) const noexcept; + + //lambda_method() :m_hopper(nullptr) {} + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp new file mode 100644 index 00000000..ae7103bc --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp @@ -0,0 +1,52 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "dispatch_interface.h" + +#include "lambda_method.h" +#include "hopper_nonconst.h" + +namespace rtl::detail +{ + + //template + //template + //inline lambda_method lambda_method::create(const functor_hop* fptr_hopper) + //{ + // return lambda_method(); + // //lambda_method(detail::TypeId::get(), fptr_hopper, + // // &hopper_nonconst::template dispatch, return_t>); + //} + + + //template + //inline decltype(auto) lambda_method::operator()(record_t& target, const signature_ts& ...params) const noexcept + //{ + // //TODO: static-assert signature_ts == args_t && enable perfect-forwarding + // return m_hopper(target, *this, params...); + //} + + + //template + //template + //inline decltype(auto) lambda_method::dispatch(record_t& target, const signature_ts&...params) const noexcept + //{ + // //TODO: static-assert signature_ts == args_t && enable perfect-forwarding + // if constexpr (std::is_same_v) { + // hopper_nonconst::template dispatch(target, *this, params...); + // } + // else { + // return hopper_nonconst::template dispatch(target, *this, params...); + // } + //} +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 768ba5cf..67c7f702 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -80,7 +80,7 @@ namespace rtl { GETTER(std::string, Namespace, m_namespace); GETTER(std::string, FunctionName, m_function); GETTER(std::size_t, RecordTypeId, m_recordTypeId); - GETTER(std::vector, Functors, m_functorIds); + GETTER(std::vector, Overloads, m_functorIds); Function() = default; Function(Function&&) = default; diff --git a/ReflectionTemplateLib/rtl/src/CxxMirror.cpp b/ReflectionTemplateLib/rtl/src/CxxMirror.cpp index 9054699d..72d8f202 100644 --- a/ReflectionTemplateLib/rtl/src/CxxMirror.cpp +++ b/ReflectionTemplateLib/rtl/src/CxxMirror.cpp @@ -32,7 +32,7 @@ namespace rtl { const Record& record = itr->second; Method ctors = record.getMethod(detail::ctor_name(record.getRecordName())).value(); - const_cast(pTarget).m_objectId.m_clonerId = ctors.getFunctors()[detail::Index::CopyCtor]; + const_cast(pTarget).m_objectId.m_clonerId = ctors.getOverloads()[detail::Index::CopyCtor]; return error::None; } return error::CloningDisabled; diff --git a/ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp b/ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp index 9905c356..fe35b583 100644 --- a/ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp +++ b/ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp @@ -40,7 +40,7 @@ static const std::string toJson(const FunctorId& pFunctorId) static const std::string toJson(const Function& pFunction) { std::stringstream sout; - const auto& functors = pFunction.getFunctors(); + const auto& functors = pFunction.getOverloads(); const std::string& record = pFunction.getRecordName(); const std::string& nmspace = pFunction.getNamespace(); From 847e1a2e93cb1c42065467f62888f816002967a3 Mon Sep 17 00:00:00 2001 From: neeraj Date: Sat, 20 Sep 2025 10:47:36 +0530 Subject: [PATCH 15/58] fixed cland/gcc compile errors, known-return reflective calls in progress. --- .../src/ReflectedCallKnownReturn.cpp | 4 +- .../rtl/builder/RObjectBuilder.h | 2 +- .../rtl/builder/SetupMethod.hpp | 4 +- .../rtl/cache/lambda_method_cache.h | 2 +- .../rtl/detail/inc/RObjectUPtr.h | 2 +- .../rtl/detail/inc/forward_decls.h | 2 + ReflectionTemplateLib/rtl/dispatch/hopper.h | 67 +++++++++-------- .../rtl/dispatch/hopper_const.h | 21 +++--- .../rtl/dispatch/hopper_ctor.h | 43 ++++++----- .../rtl/dispatch/hopper_nonconst.h | 74 +++++++++---------- .../rtl/dispatch/lambda_function.h | 10 +-- .../rtl/dispatch/lambda_function.hpp | 6 +- .../rtl/dispatch/lambda_method.h | 19 ++++- .../rtl/dispatch/lambda_method.hpp | 17 ++--- ReflectionTemplateLib/rtl/inc/RObject.h | 6 +- 15 files changed, 143 insertions(+), 136 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 9ea401fb..1c9d2293 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -114,7 +114,7 @@ void ReflectedCallKnownReturn::set(benchmark::State& state) static auto passed = _test0(); for (auto _ : state) { - if (passed) + //if (passed) { (*SendMessage_lambda).dispatch(bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); @@ -128,7 +128,7 @@ void ReflectedCallKnownReturn::get(benchmark::State& state) static auto passed = _test2(); for (auto _: state) { - if (passed) + //if (passed) { auto retStr = (*GetMessage_lambda).dispatch(bm::g_longStr); benchmark::DoNotOptimize(retStr); diff --git a/ReflectionTemplateLib/rtl/builder/RObjectBuilder.h b/ReflectionTemplateLib/rtl/builder/RObjectBuilder.h index 58b352b5..b5cd0750 100644 --- a/ReflectionTemplateLib/rtl/builder/RObjectBuilder.h +++ b/ReflectionTemplateLib/rtl/builder/RObjectBuilder.h @@ -14,7 +14,7 @@ #include #include "rtl_traits.h" -#include "forward_decls.h" +#include "RObject.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index d2ecf3d7..ca9c419a 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -21,7 +21,7 @@ #include "functor_cache_const.h" #include "functor_cache_nonconst.h" -#include "lambda_method.hpp" +#include "lambda_method.h" #include "lambda_method_cache.h" @@ -172,7 +172,7 @@ namespace rtl::detail auto& functorCache = cache::method_ptr<_recordType, _signature...>::instance(); auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambda = lambdaCache.template push<_recordType, _returnType>(functor); + auto& lambda = lambdaCache.template push<_returnType>(functor); lambdaPtr = λ }; diff --git a/ReflectionTemplateLib/rtl/cache/lambda_method_cache.h b/ReflectionTemplateLib/rtl/cache/lambda_method_cache.h index a43268ed..e86d0cb0 100644 --- a/ReflectionTemplateLib/rtl/cache/lambda_method_cache.h +++ b/ReflectionTemplateLib/rtl/cache/lambda_method_cache.h @@ -27,7 +27,7 @@ namespace rtl::cache return instance_; } - template + template const dispatch::lambda_method& push(const dispatch::functor_hop* fptr_hopper) const { m_cache.push_back(dispatch::lambda_method::template create(fptr_hopper)); diff --git a/ReflectionTemplateLib/rtl/detail/inc/RObjectUPtr.h b/ReflectionTemplateLib/rtl/detail/inc/RObjectUPtr.h index 67137208..1fd4ce58 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/RObjectUPtr.h +++ b/ReflectionTemplateLib/rtl/detail/inc/RObjectUPtr.h @@ -15,7 +15,7 @@ #include #include -#include "RObject.h" +#include "RObjectBuilder.hpp" /*------------------------------------------------------------------------------------------ RObjectUPtr diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index 0e1776b9..8f96bca2 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -25,6 +25,8 @@ namespace rtl class CxxMirror; + struct Return; + namespace detail { struct FunctorId; diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper.h b/ReflectionTemplateLib/rtl/dispatch/hopper.h index 11451ff9..00cc87ea 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper.h @@ -15,7 +15,6 @@ #include "lambda_function.h" #include "functor.h" -//#include "RObjectBuilder.hpp" namespace rtl::dispatch { @@ -37,44 +36,44 @@ namespace rtl::dispatch } - template requires (void_t == true) - static Return dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept - { - if constexpr (std::is_same_v) - { - auto functor = lambda_ref.functor().template get() - .template get(lambda_ref.m_returnId); + // template requires (void_t == true) + // static Return dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept + // { + // if constexpr (std::is_same_v) + // { + // auto functor = lambda_ref.functor().template get() + // .template get(lambda_ref.m_returnId); - (*functor)(params...); - } - else - { - static_assert("return-type mismatch."); - } - return { error::None, RObject{} }; - } + // (*functor)(params...); + // } + // else + // { + // static_assert("return-type mismatch."); + // } + // return { error::None, RObject{} }; + // } - template requires (void_t == false) - static Return dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept - { - constexpr bool isConstCastSafe = (!traits::is_const_v); + // template requires (void_t == false) + // static Return dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept + // { + // constexpr bool isConstCastSafe = (!traits::is_const_v); - auto functor = lambda_ref.functor().template get() - .template get(lambda_ref.m_returnId); + // auto functor = lambda_ref.functor().template get() + // .template get(lambda_ref.m_returnId); - if constexpr (std::is_reference_v) - { - using T = traits::raw_t; - const T& retObj = (*functor)(params...); - return { error::None, RObject{} }; - } - else { + // if constexpr (std::is_reference_v) + // { + // using T = traits::raw_t; + // const T& retObj = (*functor)(params...); + // return { error::None, RObject{} }; + // } + // else { - //auto&& retObj = (*functor)(params...); - //using T = std::remove_cvref_t; - return { error::None, RObject{} }; - } - } + // auto&& retObj = (*functor)(params...); + // using T = std::remove_cvref_t; + // return { error::None, RObject{} }; + // } + // } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_const.h b/ReflectionTemplateLib/rtl/dispatch/hopper_const.h index 00acfdc4..9134db40 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_const.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_const.h @@ -11,17 +11,18 @@ #pragma once -#include "lambda_function.h" +//#include "RObject.h" +//#include "lambda_function.h" namespace rtl::dispatch { - template - struct hopper_const - { - template - static Return dispatch(const lambda_hop&, const signature_ts&...) noexcept - { - return { error::EmptyRObject, RObject{} }; - } - }; + // template + // struct hopper_const + // { + // template + // static Return dispatch(const lambda_hop&, const signature_ts&...) noexcept + // { + // return { error::EmptyRObject, RObject{} }; + // } + // }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h b/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h index 076e6cb9..d058d568 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h @@ -12,29 +12,28 @@ #pragma once -#include "lambda_function.h" +//#include "lambda_function.h" namespace rtl::dispatch { - template - struct hopper_ctor - { - template - static Return dispatch(const lambda_hop&, const signature_ts&...) noexcept - { - return { error::EmptyRObject, RObject{} }; - } - }; - - - template - struct hopper_copyctor - { - template - static Return dispatch(const lambda_hop&, signature_ts&&...) noexcept - { - return { error::EmptyRObject, RObject{} }; - } - }; - + // template + // struct hopper_ctor + // { + // template + // static Return dispatch(const lambda_hop&, const signature_ts&...) noexcept + // { + // return { error::EmptyRObject, RObject{} }; + // } + // }; + + + // template + // struct hopper_copyctor + // { + // template + // static Return dispatch(const lambda_hop&, signature_ts&&...) noexcept + // { + // return { error::EmptyRObject, RObject{} }; + // } + // }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h index e629ad66..789b8e27 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h @@ -11,17 +11,17 @@ #pragma once -#include "forward_decls.h" +//#include "forward_decls.h" -#include "lambda_function.h" -#include "functor.h" +//#include "lambda_function.h" +//#include "functor.h" namespace rtl::dispatch { template struct hopper_nonconst { - template requires (std::is_same_v == false) + template requires (std::is_same_v == false) static decltype(auto) dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept { auto functor = lambda_ref.functor().template get_nonconst() @@ -36,44 +36,44 @@ namespace rtl::dispatch } - template requires (void_t == true) - static Return dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept - { - if constexpr (std::is_same_v) - { - auto functor = lambda_ref.functor().template get_nonconst() - .template get(lambda_ref.m_returnId); + // template requires (void_t == true) + // static Return dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept + // { + // if constexpr (std::is_same_v) + // { + // auto functor = lambda_ref.functor().template get_nonconst() + // .template get(lambda_ref.m_returnId); - (target.*functor)(params...); - } - else - { - static_assert("return-type mismatch."); - } - return { error::None, RObject{} }; - } + // (target.*functor)(params...); + // } + // else + // { + // static_assert("return-type mismatch."); + // } + // return { error::None, RObject{} }; + // } - template requires (void_t == false) - static Return dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept - { - constexpr bool isConstCastSafe = (!traits::is_const_v); + // template requires (void_t == false) + // static Return dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept + // { + // constexpr bool isConstCastSafe = (!traits::is_const_v); - auto functor = lambda_ref.functor().template get_nonconst() - .template get(lambda_ref.m_returnId); + // auto functor = lambda_ref.functor().template get_nonconst() + // .template get(lambda_ref.m_returnId); - if constexpr (std::is_reference_v) - { - using T = traits::raw_t; - const T& retObj = (target.*functor)(params...); - return { error::None, RObject{} }; - } - else { + // if constexpr (std::is_reference_v) + // { + // using T = traits::raw_t; + // const T& retObj = (target.*functor)(params...); + // return { error::None, RObject{} }; + // } + // else { - auto&& retObj = (target.*functor)(params...); - using T = std::remove_cvref_t; - return { error::None, RObject{} }; - } - } + // auto&& retObj = (target.*functor)(params...); + // using T = std::remove_cvref_t; + // return { error::None, RObject{} }; + // } + // } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 8ff7d4aa..7cc22fa4 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -42,19 +42,19 @@ namespace rtl::dispatch public: + template + static lambda create(const functor_hop*); + decltype(auto) operator()(const signature_ts&...) const noexcept; template decltype(auto) dispatch(const signature_ts&...) const noexcept; - template - static lambda create(const functor_hop*); - template static lambda create_method_const(const functor_hop* fptr_hopper) { - return lambda(detail::TypeId::get(), fptr_hopper, - &hopper_const::template dispatch); + return lambda(detail::TypeId::get(), fptr_hopper, nullptr); + //&hopper_const::template dispatch); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp index b959eb1a..fb424486 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp @@ -17,10 +17,10 @@ namespace rtl::dispatch { template template - static lambda lambda::create(const functor_hop* fptr_hopper) + inline lambda lambda::create(const functor_hop* fptr_hopper) { - return lambda(detail::TypeId::get(), fptr_hopper, - &hopper::template dispatch, return_t>); + return lambda(detail::TypeId::get(), fptr_hopper, nullptr); + //&hopper::template dispatch, return_t>); } template diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index 9cf7c1d9..94441fdc 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -11,7 +11,7 @@ #pragma once -#include "forward_decls.h" +//#include "forward_decls.h" #include "dispatch_interface.h" #include "hopper_nonconst.h" @@ -43,10 +43,21 @@ namespace rtl::dispatch //&hopper_nonconst::template dispatch, return_t>); } - decltype(auto) operator()(record_t&, const signature_ts&...) const noexcept; + decltype(auto) operator()(record_t& target, const signature_ts& ...params) const noexcept + { + return m_hopper(target, *this, params...); + } - template - decltype(auto) dispatch(record_t&, const signature_ts&...) const noexcept; + template + decltype(auto) dispatch(record_t& target, const signature_ts& ...params) const noexcept + { + if constexpr (std::is_same_v) { + hopper_nonconst::template dispatch(target, *this, params...); + } + else { + return hopper_nonconst::template dispatch(target, *this, params...); + } + } //lambda_method() :m_hopper(nullptr) {} }; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp index ae7103bc..5a0e14b3 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp @@ -11,10 +11,10 @@ #pragma once -#include "dispatch_interface.h" +//#include "dispatch_interface.h" -#include "lambda_method.h" -#include "hopper_nonconst.h" +//#include "lambda_method.h" +//#include "hopper_nonconst.h" namespace rtl::detail { @@ -37,16 +37,15 @@ namespace rtl::detail //} - //template - //template - //inline decltype(auto) lambda_method::dispatch(record_t& target, const signature_ts&...params) const noexcept - //{ - // //TODO: static-assert signature_ts == args_t && enable perfect-forwarding + // template + // template + // inline return_t lambda_method::dispatch(record_t& target, const signature_ts&...params) const noexcept + // { // if constexpr (std::is_same_v) { // hopper_nonconst::template dispatch(target, *this, params...); // } // else { // return hopper_nonconst::template dispatch(target, *this, params...); // } - //} + // } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/RObject.h b/ReflectionTemplateLib/rtl/inc/RObject.h index 58f5fc10..e91f162c 100644 --- a/ReflectionTemplateLib/rtl/inc/RObject.h +++ b/ReflectionTemplateLib/rtl/inc/RObject.h @@ -20,7 +20,7 @@ #include "rtl_typeid.h" #include "rtl_traits.h" - +#include "forward_decls.h" namespace rtl::detail { @@ -36,10 +36,6 @@ namespace rtl::detail namespace rtl { - struct Return; - class Function; - class CxxMirror; - //Reflecting the object within. class RObject { From 3bd868cc6d94103a57f028fb2ddc18c787539ca3 Mon Sep 17 00:00:00 2001 From: neeraj Date: Sat, 20 Sep 2025 14:00:14 +0530 Subject: [PATCH 16/58] better renaming for functor/method/lambda/cache --- .../src/ReflectedCallKnownReturn.cpp | 15 +-- .../rtl/builder/FunctorContainer.h | 2 +- .../rtl/builder/SetupFunction.hpp | 8 +- .../rtl/builder/SetupMethod.hpp | 16 ++-- .../rtl/cache/CMakeLists.txt | 10 +- ...cache_const.h => cache_const_method_ptr.h} | 12 +-- .../{functor_cache.h => cache_function_ptr.h} | 10 +- .../rtl/cache/cache_lambda_hop_function.h | 59 ++++++++++++ ...thod_cache.h => cache_lambda_hop_method.h} | 26 ++--- ...or_cache_nonconst.h => cache_method_ptr.h} | 10 +- .../rtl/cache/lambda_function_cache.h | 59 ------------ .../rtl/detail/inc/FunctorId.h | 12 +-- .../rtl/detail/inc/forward_decls.h | 16 +--- .../rtl/dispatch/CMakeLists.txt | 14 +-- .../{functor_const.h => const_method_ptr.h} | 4 +- .../rtl/dispatch/dispatch_interface.h | 96 ++++++++++--------- .../dispatch/{functor.h => function_ptr.h} | 6 +- ReflectionTemplateLib/rtl/dispatch/hopper.h | 8 +- .../rtl/dispatch/hopper_nonconst.h | 4 +- ...ambda_function.h => lambda_hop_function.h} | 8 +- ...a_function.hpp => lambda_hop_function.hpp} | 11 +-- .../{lambda_method.h => lambda_hop_method.h} | 10 +- ...ambda_method.hpp => lambda_hop_method.hpp} | 2 +- .../{functor_nonconst.h => method_ptr.h} | 4 +- ReflectionTemplateLib/rtl/rtl.h | 12 ++- 25 files changed, 219 insertions(+), 215 deletions(-) rename ReflectionTemplateLib/rtl/cache/{functor_cache_const.h => cache_const_method_ptr.h} (80%) rename ReflectionTemplateLib/rtl/cache/{functor_cache.h => cache_function_ptr.h} (83%) create mode 100644 ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h rename ReflectionTemplateLib/rtl/cache/{lambda_method_cache.h => cache_lambda_hop_method.h} (54%) rename ReflectionTemplateLib/rtl/cache/{functor_cache_nonconst.h => cache_method_ptr.h} (81%) delete mode 100644 ReflectionTemplateLib/rtl/cache/lambda_function_cache.h rename ReflectionTemplateLib/rtl/dispatch/{functor_const.h => const_method_ptr.h} (92%) rename ReflectionTemplateLib/rtl/dispatch/{functor.h => function_ptr.h} (90%) rename ReflectionTemplateLib/rtl/dispatch/{lambda_function.h => lambda_hop_function.h} (86%) rename ReflectionTemplateLib/rtl/dispatch/{lambda_function.hpp => lambda_hop_function.hpp} (75%) rename ReflectionTemplateLib/rtl/dispatch/{lambda_method.h => lambda_hop_method.h} (87%) rename ReflectionTemplateLib/rtl/dispatch/{lambda_method.hpp => lambda_hop_method.hpp} (96%) rename ReflectionTemplateLib/rtl/dispatch/{functor_nonconst.h => method_ptr.h} (92%) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 1c9d2293..84c36503 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -1,7 +1,8 @@ #include #include -#include +//#include +#include #include "BenchMark.h" #include "ReflectedCallKnownReturn.h" @@ -19,13 +20,13 @@ namespace cxx namespace { - static const rtl::dispatch::lambda* GetMessage_lambda = nullptr; + static const rtl::lambda_function* GetMessage_lambda = nullptr; - static const rtl::dispatch::lambda* SendMessage_lambda = nullptr; + static const rtl::lambda_function* SendMessage_lambda = nullptr; - static const rtl::dispatch::lambda* NodeGetMessage_lambda = nullptr; + static const rtl::lambda_method* NodeGetMessage_lambda = nullptr; - static const rtl::dispatch::lambda* NodeSendMessage_lambda = nullptr; + static const rtl::lambda_method* NodeSendMessage_lambda = nullptr; static const rtl::RObject nodeObj = []() { @@ -43,9 +44,9 @@ namespace SendMessage_lambda = sendMsg.getOverloads()[0].get_lambda_function(); - NodeGetMessage_lambda = getMsgNode.getOverloads()[0].get_lambda_function(); + NodeGetMessage_lambda = getMsgNode.getOverloads()[0].get_lambda_method(); - NodeSendMessage_lambda = sendMsgNode.getOverloads()[0].get_lambda_function(); + NodeSendMessage_lambda = sendMsgNode.getOverloads()[0].get_lambda_method(); auto [err, robj] = Node.create(); diff --git a/ReflectionTemplateLib/rtl/builder/FunctorContainer.h b/ReflectionTemplateLib/rtl/builder/FunctorContainer.h index 532fa188..dba8bd9a 100644 --- a/ReflectionTemplateLib/rtl/builder/FunctorContainer.h +++ b/ReflectionTemplateLib/rtl/builder/FunctorContainer.h @@ -15,12 +15,12 @@ #include #include -#include "lambda_function_cache.h" #include "rtl_constants.h" #include "CallReflector.h" #include "SetupFunction.h" #include "SetupConstructor.h" + namespace rtl { namespace detail diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index 5be59247..65479e5d 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -13,9 +13,9 @@ #include -#include "functor_cache.h" -#include "lambda_function.hpp" -#include "lambda_function_cache.h" +#include "lambda_hop_function.hpp" +#include "cache_lambda_hop_function.h" +#include "cache_function_ptr.h" #include "SetupFunction.h" #include "RObjectBuilder.hpp" @@ -94,7 +94,7 @@ namespace rtl const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = cache::lambda_function<_signature...>::instance(); + auto& lambdaCache = cache::lambda_hop_function<_signature...>::instance(); auto& functorCache = cache::function_ptr<_signature...>::instance(); auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); auto& lambda = lambdaCache.template push<_returnType>(functor); diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index ca9c419a..424d0361 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -18,12 +18,10 @@ #include "SetupMethod.h" #include "RObjectBuilder.hpp" -#include "functor_cache_const.h" -#include "functor_cache_nonconst.h" - -#include "lambda_method.h" -#include "lambda_method_cache.h" - +#include "lambda_hop_method.h" +#include "cache_method_ptr.h" +#include "cache_const_method_ptr.h" +#include "cache_lambda_hop_method.h" namespace rtl::detail { @@ -168,8 +166,8 @@ namespace rtl::detail const dispatch::lambda_hop* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = cache::lambda_method<_recordType, _signature...>::instance(); auto& functorCache = cache::method_ptr<_recordType, _signature...>::instance(); + auto& lambdaCache = cache::lambda_hop_method<_recordType, _signature...>::instance(); auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); auto& lambda = lambdaCache.template push<_returnType>(functor); @@ -239,11 +237,11 @@ namespace rtl::detail const dispatch::lambda_hop* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = cache::lambda_function<_signature...>::instance(); + auto& lambdaCache = cache::lambda_hop_method<_recordType, _signature...>::instance(); auto& functorCache = cache::const_method_ptr<_recordType, _signature...>::instance(); auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambda = lambdaCache.template push_method_const<_recordType, _returnType>(functor); + auto& lambda = lambdaCache.template push<_returnType>(functor); lambdaPtr = λ }; diff --git a/ReflectionTemplateLib/rtl/cache/CMakeLists.txt b/ReflectionTemplateLib/rtl/cache/CMakeLists.txt index e31be8d4..24ac7968 100644 --- a/ReflectionTemplateLib/rtl/cache/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/cache/CMakeLists.txt @@ -2,11 +2,11 @@ # Collect headers (absolute paths) set(LOCAL_HEADERS - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method_cache.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function_cache.h" - "${CMAKE_CURRENT_SOURCE_DIR}/functor_cache.h" - "${CMAKE_CURRENT_SOURCE_DIR}/functor_cache_const.h" - "${CMAKE_CURRENT_SOURCE_DIR}/functor_cache_nonconst.h" + "${CMAKE_CURRENT_SOURCE_DIR}/cache_lambda_hop_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/cache_lambda_hop_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/cache_function_ptr.h" + "${CMAKE_CURRENT_SOURCE_DIR}/cache_method_ptr.h" + "${CMAKE_CURRENT_SOURCE_DIR}/cache_const_method_ptr.h" ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_const.h b/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h similarity index 80% rename from ReflectionTemplateLib/rtl/cache/functor_cache_const.h rename to ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h index c1775fce..163bbffa 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache_const.h +++ b/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h @@ -13,14 +13,14 @@ #include -#include "functor_const.h" +#include "const_method_ptr.h" namespace rtl::cache { template struct const_method_ptr { - using functor_t = dispatch::functor_const; + using functor_t = dispatch::const_method_ptr; static const const_method_ptr& instance() { @@ -29,9 +29,9 @@ namespace rtl::cache } template - const dispatch::functor_hop* push(return_t(record_t::* fptr)(signature_ts...) const, std::size_t lambda_index) const + const dispatch::functor* push(return_t(record_t::* fptr)(signature_ts...) const, std::size_t lambda_index) const { - using voidfn_t = typename dispatch::functor_const::voidfn_t; + using voidfn_t = typename dispatch::const_method_ptr::voidfn_t; auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); m_cache.emplace_back(std::make_pair(functor, lambda_index)); return &(m_cache.back().first); @@ -39,7 +39,7 @@ namespace rtl::cache } template - std::pair find(return_t(record_t::* fptr)(signature_ts...) const) const + std::pair find(return_t(record_t::* fptr)(signature_ts...) const) const { for (auto& itr : m_cache) { @@ -61,6 +61,6 @@ namespace rtl::cache // No reallocation occurs; original objects stay intact mutable std::list> m_cache; - const_method_ptr() {} + const_method_ptr() = default; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache.h b/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h similarity index 83% rename from ReflectionTemplateLib/rtl/cache/functor_cache.h rename to ReflectionTemplateLib/rtl/cache/cache_function_ptr.h index 484ee6e0..5552fc0a 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache.h +++ b/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h @@ -13,14 +13,14 @@ #include -#include "functor.h" +#include "function_ptr.h" namespace rtl::cache { template struct function_ptr { - using functor_t = dispatch::functor; + using functor_t = dispatch::function_ptr; static const function_ptr& instance() { @@ -29,9 +29,9 @@ namespace rtl::cache } template - const dispatch::functor_hop* push(return_t(*fptr)(signature_ts...), std::size_t lambda_index) const + const dispatch::functor* push(return_t(*fptr)(signature_ts...), std::size_t lambda_index) const { - using voidfn_t = typename dispatch::functor::voidfn_t; + using voidfn_t = typename dispatch::function_ptr::voidfn_t; auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); m_cache.emplace_back(std::make_pair(functor , lambda_index)); @@ -39,7 +39,7 @@ namespace rtl::cache } template - std::pair find(return_t(*fptr)(signature_ts...)) const + std::pair find(return_t(*fptr)(signature_ts...)) const { for (auto& itr : m_cache) { diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h new file mode 100644 index 00000000..941a24b2 --- /dev/null +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h @@ -0,0 +1,59 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include + +#include "lambda_hop_function.h" + +namespace rtl::cache +{ + template + struct lambda_hop_function + { + static const lambda_hop_function& instance() + { + static const lambda_hop_function instance_; + return instance_; + } + + template + const dispatch::lambda_hop_function& push(const dispatch::functor* fptr_hopper) const + { + m_cache.push_back(dispatch::lambda_hop_function::template create(fptr_hopper)); + const dispatch::lambda_hop_function& lambda_hop = m_cache.back(); + fptr_hopper->set_lambda(&lambda_hop); + return lambda_hop; + } + + template + const dispatch::lambda_hop_function& push_method_const(const dispatch::functor* fptr_hopper) const + { + m_cache.push_back(dispatch::lambda_hop_function::template create_method_const(fptr_hopper)); + const dispatch::lambda_hop_function& lambda_hop = m_cache.back(); + fptr_hopper->set_lambda(&lambda_hop); + return lambda_hop; + } + + lambda_hop_function(lambda_hop_function&&) = delete; + lambda_hop_function(const lambda_hop_function&) = delete; + lambda_hop_function& operator=(lambda_hop_function&&) = delete; + lambda_hop_function& operator=(const lambda_hop_function&) = delete; + + private: + + // No reallocation occurs; original objects stay intact + mutable std::list> m_cache; + + lambda_hop_function() = default; + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/lambda_method_cache.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h similarity index 54% rename from ReflectionTemplateLib/rtl/cache/lambda_method_cache.h rename to ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h index e86d0cb0..3e814eb1 100644 --- a/ReflectionTemplateLib/rtl/cache/lambda_method_cache.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h @@ -13,39 +13,39 @@ #include -#include "lambda_function.h" +#include "lambda_hop_method.h" namespace rtl::cache { template - struct lambda_method + struct lambda_hop_method { - static const lambda_method& instance() + static const lambda_hop_method& instance() { - static const lambda_method instance_; + static const lambda_hop_method instance_; return instance_; } template - const dispatch::lambda_method& push(const dispatch::functor_hop* fptr_hopper) const + const dispatch::lambda_hop_method& push(const dispatch::functor* fptr_hopper) const { - m_cache.push_back(dispatch::lambda_method::template create(fptr_hopper)); - const dispatch::lambda_method& lambda_hop = m_cache.back(); + m_cache.push_back(dispatch::lambda_hop_method::template create(fptr_hopper)); + const dispatch::lambda_hop_method& lambda_hop = m_cache.back(); fptr_hopper->set_lambda(&lambda_hop); return lambda_hop; } - lambda_method(lambda_method&&) = delete; - lambda_method(const lambda_method&) = delete; - lambda_method& operator=(lambda_method&&) = delete; - lambda_method& operator=(const lambda_method&) = delete; + lambda_hop_method(lambda_hop_method&&) = delete; + lambda_hop_method(const lambda_hop_method&) = delete; + lambda_hop_method& operator=(lambda_hop_method&&) = delete; + lambda_hop_method& operator=(const lambda_hop_method&) = delete; private: // No reallocation occurs; original objects stay intact - mutable std::list> m_cache; + mutable std::list> m_cache; - lambda_method() {} + lambda_hop_method() = default; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h b/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h similarity index 81% rename from ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h rename to ReflectionTemplateLib/rtl/cache/cache_method_ptr.h index 41e67629..05e63d2a 100644 --- a/ReflectionTemplateLib/rtl/cache/functor_cache_nonconst.h +++ b/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h @@ -13,14 +13,14 @@ #include -#include "functor_nonconst.h" +#include "method_ptr.h" namespace rtl::cache { template struct method_ptr { - using functor_t = dispatch::functor_nonconst; + using functor_t = dispatch::method_ptr; static const method_ptr& instance() { @@ -29,16 +29,16 @@ namespace rtl::cache } template - const dispatch::functor_hop* push(return_t(record_t::* fptr)(signature_ts...), std::size_t lambda_index) const + const dispatch::functor* push(return_t(record_t::* fptr)(signature_ts...), std::size_t lambda_index) const { - using voidfn_t = typename dispatch::functor_nonconst::voidfn_t; + using voidfn_t = typename dispatch::method_ptr::voidfn_t; auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); m_cache.emplace_back(std::make_pair(functor, lambda_index)); return &(m_cache.back().first); } template - std::pair find(return_t(record_t::* fptr)(signature_ts...)) const + std::pair find(return_t(record_t::* fptr)(signature_ts...)) const { for (auto& itr : m_cache) { diff --git a/ReflectionTemplateLib/rtl/cache/lambda_function_cache.h b/ReflectionTemplateLib/rtl/cache/lambda_function_cache.h deleted file mode 100644 index fae533a3..00000000 --- a/ReflectionTemplateLib/rtl/cache/lambda_function_cache.h +++ /dev/null @@ -1,59 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include - -#include "lambda_function.h" - -namespace rtl::cache -{ - template - struct lambda_function - { - static const lambda_function& instance() - { - static const lambda_function instance_; - return instance_; - } - - template - const dispatch::lambda& push(const dispatch::functor_hop* fptr_hopper) const - { - m_cache.push_back(dispatch::lambda::template create(fptr_hopper)); - const dispatch::lambda& lambda_hop = m_cache.back(); - fptr_hopper->set_lambda(&lambda_hop); - return lambda_hop; - } - - template - const dispatch::lambda& push_method_const(const dispatch::functor_hop* fptr_hopper) const - { - m_cache.push_back(dispatch::lambda::template create_method_const(fptr_hopper)); - const dispatch::lambda& lambda_hop = m_cache.back(); - fptr_hopper->set_lambda(&lambda_hop); - return lambda_hop; - } - - lambda_function(lambda_function&&) = delete; - lambda_function(const lambda_function&) = delete; - lambda_function& operator=(lambda_function&&) = delete; - lambda_function& operator=(const lambda_function&) = delete; - - private: - - // No reallocation occurs; original objects stay intact - mutable std::list> m_cache; - - lambda_function() {} - }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index 6514cfc2..b5976e80 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -14,8 +14,8 @@ #include "rtl_typeid.h" #include "rtl_constants.h" #include "forward_decls.h" -#include "lambda_method.h" -#include "lambda_function.h" +#include "lambda_hop_method.h" +#include "lambda_hop_function.h" namespace rtl::detail { @@ -52,13 +52,13 @@ namespace rtl::detail GETTER(std::string, SignatureStr, m_signature) template - const dispatch::lambda<_signature...>* get_lambda_function() const { + const dispatch::lambda_hop_function<_signature...>* get_lambda_function() const { return m_lambda->get_function<_signature...>(); } - template - const dispatch::lambda_method<_signature...>* get_lambda_method() const { - return m_lambda->get_method(); + template + const dispatch::lambda_hop_method<_recordType, _signature...>* get_lambda_method() const { + return m_lambda->get_method<_recordType, _signature...>(); } /* @method: getHashCode() diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index 8f96bca2..3657de57 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -24,8 +24,6 @@ namespace rtl class Method; class CxxMirror; - - struct Return; namespace detail { @@ -37,23 +35,19 @@ namespace rtl namespace dispatch { - struct lambda_hop; - - struct functor_hop; - template - class lambda; + class lambda_hop_function; template - class lambda_method; + class lambda_hop_method; template - struct functor; + struct function_ptr; template - struct functor_const; + struct const_method_ptr; template - struct functor_nonconst; + struct method_ptr; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt index 45ffd2a7..6071378d 100644 --- a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt @@ -4,14 +4,14 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/dispatch_interface.h" - "${CMAKE_CURRENT_SOURCE_DIR}/functor.h" - "${CMAKE_CURRENT_SOURCE_DIR}/functor_const.h" - "${CMAKE_CURRENT_SOURCE_DIR}/functor_nonconst.h" + "${CMAKE_CURRENT_SOURCE_DIR}/function_ptr.h" + "${CMAKE_CURRENT_SOURCE_DIR}/const_method_ptr.h" + "${CMAKE_CURRENT_SOURCE_DIR}/method_ptr.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method.hpp" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_method.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_function.hpp" "${CMAKE_CURRENT_SOURCE_DIR}/hopper.h" "${CMAKE_CURRENT_SOURCE_DIR}/hopper_ctor.h" "${CMAKE_CURRENT_SOURCE_DIR}/hopper_const.h" diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_const.h b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h similarity index 92% rename from ReflectionTemplateLib/rtl/dispatch/functor_const.h rename to ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h index 7a0ae4b9..8f02294a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor_const.h +++ b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h @@ -18,7 +18,7 @@ namespace rtl::dispatch { template - struct functor_const : public functor_hop + struct const_method_ptr : public functor { using voidfn_t = void(record_t::*)(signature_ts...) const; @@ -39,7 +39,7 @@ namespace rtl::dispatch return (m_functor == reinterpret_cast(fptr)); } - functor_const(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) + const_method_ptr(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) { m_returnId = returnId; m_signatureId = detail::TypeId>::get(); diff --git a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h b/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h index 6c720eb0..413cf06f 100644 --- a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h +++ b/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h @@ -16,12 +16,55 @@ #include "rtl_traits.h" #include "rtl_typeid.h" #include "rtl_constants.h" +#include "forward_decls.h" + + +namespace rtl::dispatch +{ + struct lambda_hop; + + struct functor + { + void set_lambda(const lambda_hop* lambda) const + { + m_lambda = lambda; + } + + template + const function_ptr& get() const + { + return *(static_cast*>(this)); + } + + template + const const_method_ptr& get_const() const + { + return *(static_cast*>(this)); + } + + template + const method_ptr& get_nonconst() const + { + return *(static_cast*>(this)); + } + +// protected: + + mutable const lambda_hop* m_lambda = nullptr; + + std::size_t m_recordId = detail::TypeId<>::None; + std::size_t m_returnId = detail::TypeId<>::None; + std::size_t m_signatureId = detail::TypeId<>::None; + detail::methodQ m_qualifier = detail::methodQ::None; + }; +} + namespace rtl::dispatch { struct lambda_hop { - const functor_hop& functor() const + const functor& get_functor() const { return *m_functor; } @@ -46,71 +89,32 @@ namespace rtl::dispatch } template - const lambda* get_function() const - { + const lambda_hop_function* get_function() const + { std::size_t typeId = detail::TypeId>::get(); if (typeId == m_signatureId) { - return static_cast*>(this); + return static_cast*>(this); } return nullptr; } template - const lambda_method* get_method() const + const lambda_hop_method* get_method() const { std::size_t recordId = detail::TypeId::get(); std::size_t typeId = detail::TypeId>::get(); if (typeId == m_signatureId && recordId == m_recordId) { - return static_cast*>(this); + return static_cast*>(this); } return nullptr; } // protected: - const functor_hop* m_functor = nullptr; + const functor* m_functor = nullptr; std::size_t m_recordId = detail::TypeId<>::None; std::size_t m_returnId = detail::TypeId<>::None; std::size_t m_signatureId = detail::TypeId<>::None; std::vector m_argumentsId = {}; }; -} - - -namespace rtl::dispatch -{ - struct functor_hop - { - void set_lambda(const lambda_hop* lambda) const - { - m_lambda = lambda; - } - - template - const functor& get() const - { - return *(static_cast*>(this)); - } - - template - const functor_const& get_const() const - { - return *(static_cast*>(this)); - } - - template - const functor_nonconst& get_nonconst() const - { - return *(static_cast*>(this)); - } - -// protected: - - mutable const lambda_hop* m_lambda = nullptr; - - std::size_t m_recordId = detail::TypeId<>::None; - std::size_t m_returnId = detail::TypeId<>::None; - std::size_t m_signatureId = detail::TypeId<>::None; - detail::methodQ m_qualifier = detail::methodQ::None; - }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/function_ptr.h similarity index 90% rename from ReflectionTemplateLib/rtl/dispatch/functor.h rename to ReflectionTemplateLib/rtl/dispatch/function_ptr.h index 886551e6..46506099 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/function_ptr.h @@ -16,7 +16,7 @@ namespace rtl::dispatch { template - struct functor: public functor_hop + struct function_ptr: public functor { using voidfn_t = void(*)(signature_ts...); @@ -37,13 +37,13 @@ namespace rtl::dispatch return (m_functor == reinterpret_cast(fptr)); } - functor(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) + function_ptr(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) { m_returnId = returnId; m_signatureId = detail::TypeId>::get(); } - functor(const functor&) = default; + function_ptr(const function_ptr&) = default; private: diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper.h b/ReflectionTemplateLib/rtl/dispatch/hopper.h index 00cc87ea..7e08e20d 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper.h @@ -13,8 +13,8 @@ #include -#include "lambda_function.h" -#include "functor.h" +#include "lambda_hop_function.h" +#include "function_ptr.h" namespace rtl::dispatch { @@ -24,8 +24,8 @@ namespace rtl::dispatch template requires (std::is_same_v == false) static decltype(auto) dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept { - auto functor = lambda_ref.functor().template get() - .template get(lambda_ref.m_returnId); + auto functor = lambda_ref.get_functor().template get() + .template get(lambda_ref.m_returnId); if constexpr (std::is_same_v) { (*functor)(params...); diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h index 789b8e27..d5f8c978 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h @@ -24,8 +24,8 @@ namespace rtl::dispatch template requires (std::is_same_v == false) static decltype(auto) dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept { - auto functor = lambda_ref.functor().template get_nonconst() - .template get(lambda_ref.m_returnId); + auto functor = lambda_ref.get_functor().template get_nonconst() + .template get(lambda_ref.m_returnId); if constexpr (std::is_same_v) { (target.*functor)(params...); diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h similarity index 86% rename from ReflectionTemplateLib/rtl/dispatch/lambda_function.h rename to ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h index 7cc22fa4..a1615d6f 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h @@ -25,13 +25,13 @@ namespace rtl::dispatch { template - class lambda: public lambda_hop + class lambda_hop_function: public lambda_hop { using lambda_t = std::function; const lambda_t m_hopper; - lambda(std::size_t returnId, const functor_hop* functor, lambda_t hopper) noexcept + lambda_hop_function(std::size_t returnId, const functor* functor, lambda_t hopper) noexcept : m_hopper(std::move(hopper)) { m_functor = functor; @@ -43,7 +43,7 @@ namespace rtl::dispatch public: template - static lambda create(const functor_hop*); + static lambda_hop_function create(const functor*); decltype(auto) operator()(const signature_ts&...) const noexcept; @@ -51,7 +51,7 @@ namespace rtl::dispatch decltype(auto) dispatch(const signature_ts&...) const noexcept; template - static lambda create_method_const(const functor_hop* fptr_hopper) + static lambda_hop_function create_method_const(const functor* fptr_hopper) { return lambda(detail::TypeId::get(), fptr_hopper, nullptr); //&hopper_const::template dispatch); diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp similarity index 75% rename from ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp rename to ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp index fb424486..8a22e556 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp @@ -11,29 +11,28 @@ #pragma once -#include "lambda_function.h" +#include "lambda_hop_function.h" namespace rtl::dispatch { template template - inline lambda lambda::create(const functor_hop* fptr_hopper) + inline lambda_hop_function lambda_hop_function::create(const functor* fptr_hopper) { - return lambda(detail::TypeId::get(), fptr_hopper, nullptr); + return lambda_hop_function(detail::TypeId::get(), fptr_hopper, nullptr); //&hopper::template dispatch, return_t>); } template - inline decltype(auto) lambda::operator()(const signature_ts& ...params) const noexcept + inline decltype(auto) lambda_hop_function::operator()(const signature_ts& ...params) const noexcept { //TODO: static-assert signature_ts == args_t. return m_hopper(*this, params...); } - template template - inline decltype(auto) lambda::dispatch(const signature_ts&...params) const noexcept + inline decltype(auto) lambda_hop_function::dispatch(const signature_ts&...params) const noexcept { //TODO: static-assert signature_ts == args_t. if constexpr (std::is_same_v) { diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h similarity index 87% rename from ReflectionTemplateLib/rtl/dispatch/lambda_method.h rename to ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h index 94441fdc..734ae0de 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h @@ -18,13 +18,13 @@ namespace rtl::dispatch { template - class lambda_method : public lambda_hop + class lambda_hop_method : public lambda_hop { using lambda_t = std::function; const lambda_t m_hopper; - lambda_method(std::size_t returnId, const functor_hop* functor, lambda_t hopper) noexcept + lambda_hop_method(std::size_t returnId, const functor* functor, lambda_t hopper) noexcept : m_hopper(std::move(hopper)) { m_functor = functor; @@ -37,9 +37,9 @@ namespace rtl::dispatch public: template - static lambda_method create(const functor_hop* fptr_hopper) + static lambda_hop_method create(const functor* fptr_hopper) { - return lambda_method(detail::TypeId::get(), fptr_hopper, nullptr); + return lambda_hop_method(detail::TypeId::get(), fptr_hopper, nullptr); //&hopper_nonconst::template dispatch, return_t>); } @@ -58,7 +58,5 @@ namespace rtl::dispatch return hopper_nonconst::template dispatch(target, *this, params...); } } - - //lambda_method() :m_hopper(nullptr) {} }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp similarity index 96% rename from ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp rename to ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp index 5a0e14b3..2a92ccac 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp @@ -21,7 +21,7 @@ namespace rtl::detail //template //template - //inline lambda_method lambda_method::create(const functor_hop* fptr_hopper) + //inline lambda_method lambda_method::create(const functor* fptr_hopper) //{ // return lambda_method(); // //lambda_method(detail::TypeId::get(), fptr_hopper, diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h similarity index 92% rename from ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h rename to ReflectionTemplateLib/rtl/dispatch/method_ptr.h index f42e3e64..077d4117 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor_nonconst.h +++ b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h @@ -18,7 +18,7 @@ namespace rtl::dispatch { template - struct functor_nonconst : public functor_hop + struct method_ptr : public functor { using voidfn_t = void(record_t::*)(signature_ts...); @@ -39,7 +39,7 @@ namespace rtl::dispatch return (m_functor == reinterpret_cast(fptr)); } - functor_nonconst(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) + method_ptr(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) { m_returnId = returnId; m_signatureId = detail::TypeId>::get(); diff --git a/ReflectionTemplateLib/rtl/rtl.h b/ReflectionTemplateLib/rtl/rtl.h index d4185e61..9a803b14 100644 --- a/ReflectionTemplateLib/rtl/rtl.h +++ b/ReflectionTemplateLib/rtl/rtl.h @@ -99,4 +99,14 @@ * * Declared in namespace rtl. */ -#include "CxxMirror.hpp" \ No newline at end of file +#include "CxxMirror.hpp" + + +namespace rtl { + + template + using lambda_function = dispatch::lambda_hop_function; + + template + using lambda_method = dispatch::lambda_hop_method; +} \ No newline at end of file From 5e37927e46c9308c2bf29ed6a7df08c4de9dbb24 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Sat, 20 Sep 2025 20:44:47 +0530 Subject: [PATCH 17/58] added raw-functor access interface, perfect-forwarding. --- .../src/ReflectedCallKnownReturn.cpp | 110 ++++++++++-------- .../src/ReflectedCallKnownReturn.h | 8 ++ RTLBenchmarkApp/src/main.cpp | 3 + .../rtl/cache/cache_lambda_hop_function.h | 19 +-- .../rtl/cache/cache_lambda_hop_method.h | 10 +- .../rtl/detail/inc/FunctorId.h | 11 +- .../rtl/detail/inc/forward_decls.h | 4 + .../rtl/dispatch/CMakeLists.txt | 5 +- .../rtl/dispatch/const_method_ptr.h | 12 +- .../rtl/dispatch/function_ptr.h | 16 +-- ReflectionTemplateLib/rtl/dispatch/functor.h | 60 ++++++++++ ReflectionTemplateLib/rtl/dispatch/hopper.h | 15 ++- .../{dispatch_interface.h => lambda_hop.h} | 60 ++-------- .../rtl/dispatch/lambda_hop_function.h | 9 +- .../rtl/dispatch/lambda_hop_function.hpp | 15 +-- .../rtl/dispatch/lambda_hop_method.h | 2 +- .../rtl/dispatch/lambda_hop_method.hpp | 3 +- .../rtl/dispatch/method_ptr.h | 12 +- ReflectionTemplateLib/rtl/inc/Function.h | 4 + ReflectionTemplateLib/rtl/inc/Function.hpp | 10 ++ ReflectionTemplateLib/rtl/inc/Method.h | 4 + ReflectionTemplateLib/rtl/inc/Method.hpp | 12 ++ 22 files changed, 224 insertions(+), 180 deletions(-) create mode 100644 ReflectionTemplateLib/rtl/dispatch/functor.h rename ReflectionTemplateLib/rtl/dispatch/{dispatch_interface.h => lambda_hop.h} (61%) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 84c36503..f8f06598 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -20,40 +20,33 @@ namespace cxx namespace { - static const rtl::lambda_function* GetMessage_lambda = nullptr; - - static const rtl::lambda_function* SendMessage_lambda = nullptr; + static const rtl::lambda_function& getMessage_lambda = []() + { + return *(cxx::mirror().getFunction("getMessage")->lambda_hop()); + }(); - static const rtl::lambda_method* NodeGetMessage_lambda = nullptr; + static const rtl::lambda_function& sendMessage_lambda = []() + { + return *(cxx::mirror().getFunction("sendMessage")->lambda_hop()); + }(); - static const rtl::lambda_method* NodeSendMessage_lambda = nullptr; + static const rtl::lambda_method& getMessageOnNode_lambda = []() + { + return *(cxx::mirror().getRecord("Node")->getMethod("getMessage")->lambda_hop()); + }(); - static const rtl::RObject nodeObj = []() + static const rtl::lambda_method& sendMessageOnNode_lambda = []() { rtl::Record Node = cxx::mirror().getRecord("Node").value(); + return *(cxx::mirror().getRecord("Node")->getMethod("sendMessage")->lambda_hop()); + }(); - rtl::Method getMsgNode = Node.getMethod("getMessage").value(); - - rtl::Method sendMsgNode = Node.getMethod("sendMessage").value(); - - rtl::Function getMsg = cxx::mirror().getFunction("getMessage").value(); - - rtl::Function sendMsg = cxx::mirror().getFunction("sendMessage").value(); - - GetMessage_lambda = getMsg.getOverloads()[0].get_lambda_function(); - - SendMessage_lambda = sendMsg.getOverloads()[0].get_lambda_function(); - - NodeGetMessage_lambda = getMsgNode.getOverloads()[0].get_lambda_method(); - - NodeSendMessage_lambda = sendMsgNode.getOverloads()[0].get_lambda_method(); - - auto [err, robj] = Node.create(); - + static const rtl::RObject nodeObj = []() + { + auto [err, robj] = cxx::mirror().getRecord("Node")->create(); if (robj.isEmpty()) { std::cout << "[0] error: " << rtl::to_string(err) << "\n"; } - return std::move(robj); }(); } @@ -63,9 +56,8 @@ namespace { static auto _test0 = []() { - if( SendMessage_lambda == nullptr || - !SendMessage_lambda->is_returning() || - !SendMessage_lambda->is_signature()) + if(!sendMessage_lambda.is_signature() || + !sendMessage_lambda.is_returning()) { std::cout << "[0] error: signature mismatch.\n"; return false; @@ -74,22 +66,21 @@ namespace }; - static auto _test1 = []() - { - if (NodeSendMessage_lambda == nullptr) - { - std::cout << "[1] error: signature mismatch.\n"; - return false; - } - return true; - }; + //static auto _test1 = []() + //{ + // if (sendMessageOnNode_lambda == nullptr) + // { + // std::cout << "[1] error: signature mismatch.\n"; + // return false; + // } + // return true; + //}; static auto _test2 = []() { - if ( GetMessage_lambda == nullptr || - !GetMessage_lambda->is_returning() || - !GetMessage_lambda->is_signature()) + if (!getMessage_lambda.is_signature() || + !getMessage_lambda.is_returning()) { std::cout << "[0] error: signature mismatch.\n"; return false; @@ -97,15 +88,34 @@ namespace return true; }; - static auto _test3 = []() + //static auto _test3 = []() + //{ + // if (getMessageOnNode_lambda == nullptr) + // { + // std::cout << "[3] error: signature mismatch.\n"; + // return false; + // } + // return true; + //}; +} + + +void FunctionPointerCall::set(benchmark::State& state) +{ + static auto passed = _test0(); + + // Unchecked: Passing an incorrect signature or return type is undefined behaviour. + // No validation is performed and the function will not return nullptr on mismatch. + static auto functor = sendMessage_lambda.get_functor().template args_t() + .template return_t(); + for (auto _ : state) { - if (NodeGetMessage_lambda == nullptr) + if (passed) { - std::cout << "[3] error: signature mismatch.\n"; - return false; + (*functor)(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); } - return true; - }; + } } @@ -115,9 +125,9 @@ void ReflectedCallKnownReturn::set(benchmark::State& state) static auto passed = _test0(); for (auto _ : state) { - //if (passed) + if (passed) { - (*SendMessage_lambda).dispatch(bm::g_longStr); + sendMessage_lambda.dispatch(bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } @@ -129,9 +139,9 @@ void ReflectedCallKnownReturn::get(benchmark::State& state) static auto passed = _test2(); for (auto _: state) { - //if (passed) + if (passed) { - auto retStr = (*GetMessage_lambda).dispatch(bm::g_longStr); + auto retStr = getMessage_lambda.dispatch(bm::g_longStr); benchmark::DoNotOptimize(retStr); } } diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h index 42a9011f..7084e5fa 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h @@ -10,6 +10,14 @@ struct ReflectedCallKnownReturn }; +struct FunctionPointerCall +{ + static void set(benchmark::State& state); + + static void get(benchmark::State& state); +}; + + struct ReflectedMethodCallKnownReturn { static void set(benchmark::State& state); diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index 77914b8a..c632e469 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -8,6 +8,9 @@ #include "ReflectedCallUnknownReturn.h" BENCHMARK(NativeCall::set); +BENCHMARK(FunctionPointerCall::set); +//BENCHMARK(ReflectedCallKnownReturn::set); +//BENCHMARK(ReflectedCallKnownReturn::set); BENCHMARK(StdFunctionCall::set); BENCHMARK(ReflectedCallKnownReturn::set); diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h index 941a24b2..ffc6109d 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h @@ -27,21 +27,12 @@ namespace rtl::cache } template - const dispatch::lambda_hop_function& push(const dispatch::functor* fptr_hopper) const + const dispatch::lambda_hop_function& push(const dispatch::functor* fptr) const { - m_cache.push_back(dispatch::lambda_hop_function::template create(fptr_hopper)); - const dispatch::lambda_hop_function& lambda_hop = m_cache.back(); - fptr_hopper->set_lambda(&lambda_hop); - return lambda_hop; - } - - template - const dispatch::lambda_hop_function& push_method_const(const dispatch::functor* fptr_hopper) const - { - m_cache.push_back(dispatch::lambda_hop_function::template create_method_const(fptr_hopper)); - const dispatch::lambda_hop_function& lambda_hop = m_cache.back(); - fptr_hopper->set_lambda(&lambda_hop); - return lambda_hop; + auto lambda = dispatch::lambda_hop_function::template create(fptr); + m_cache.push_back(lambda); + fptr->set_lambda(&m_cache.back()); + return m_cache.back(); } lambda_hop_function(lambda_hop_function&&) = delete; diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h index 3e814eb1..a2e02f64 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h @@ -28,12 +28,12 @@ namespace rtl::cache } template - const dispatch::lambda_hop_method& push(const dispatch::functor* fptr_hopper) const + const dispatch::lambda_hop_method& push(const dispatch::functor* fptr) const { - m_cache.push_back(dispatch::lambda_hop_method::template create(fptr_hopper)); - const dispatch::lambda_hop_method& lambda_hop = m_cache.back(); - fptr_hopper->set_lambda(&lambda_hop); - return lambda_hop; + auto lambda = dispatch::lambda_hop_method::template create(fptr); + m_cache.push_back(lambda); + fptr->set_lambda(&m_cache.back()); + return m_cache.back(); } lambda_hop_method(lambda_hop_method&&) = delete; diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index b5976e80..7dd8a163 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -15,7 +15,7 @@ #include "rtl_constants.h" #include "forward_decls.h" #include "lambda_hop_method.h" -#include "lambda_hop_function.h" + namespace rtl::detail { @@ -51,15 +51,6 @@ namespace rtl::detail GETTER(std::size_t, SignatureId, m_containerId) GETTER(std::string, SignatureStr, m_signature) - template - const dispatch::lambda_hop_function<_signature...>* get_lambda_function() const { - return m_lambda->get_function<_signature...>(); - } - - template - const dispatch::lambda_hop_method<_recordType, _signature...>* get_lambda_method() const { - return m_lambda->get_method<_recordType, _signature...>(); - } /* @method: getHashCode() @return: std::size_t (a unique hash-code for a functor) diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index 3657de57..16317a9a 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -35,6 +35,10 @@ namespace rtl namespace dispatch { + struct functor; + + class lambda_hop; + template class lambda_hop_function; diff --git a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt index 6071378d..3d512652 100644 --- a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt @@ -3,11 +3,12 @@ # Collect headers in this folder (absolute paths) set(LOCAL_HEADERS - "${CMAKE_CURRENT_SOURCE_DIR}/dispatch_interface.h" + "${CMAKE_CURRENT_SOURCE_DIR}/functor.h" "${CMAKE_CURRENT_SOURCE_DIR}/function_ptr.h" - "${CMAKE_CURRENT_SOURCE_DIR}/const_method_ptr.h" "${CMAKE_CURRENT_SOURCE_DIR}/method_ptr.h" + "${CMAKE_CURRENT_SOURCE_DIR}/const_method_ptr.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop.h" "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_method.h" "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_method.hpp" "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_function.h" diff --git a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h index 8f02294a..04cad3cc 100644 --- a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h @@ -13,7 +13,7 @@ #include -#include "dispatch_interface.h" +#include "functor.h" namespace rtl::dispatch { @@ -23,18 +23,14 @@ namespace rtl::dispatch using voidfn_t = void(record_t::*)(signature_ts...) const; template - decltype(auto) get(std::size_t returnId) const + constexpr decltype(auto) return_t() const { using fptr_t = return_t(record_t::*)(signature_ts...); - if (returnId == m_returnId) - { - return reinterpret_cast(m_functor); - } - return static_cast(nullptr); + return reinterpret_cast(m_functor); } template - bool is_same(return_t(record_t::*fptr)(signature_ts...) const) const + constexpr bool is_same(return_t(record_t::*fptr)(signature_ts...) const) const { return (m_functor == reinterpret_cast(fptr)); } diff --git a/ReflectionTemplateLib/rtl/dispatch/function_ptr.h b/ReflectionTemplateLib/rtl/dispatch/function_ptr.h index 46506099..2fe0b843 100644 --- a/ReflectionTemplateLib/rtl/dispatch/function_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/function_ptr.h @@ -11,7 +11,7 @@ #pragma once -#include "dispatch_interface.h" +#include "functor.h" namespace rtl::dispatch { @@ -20,19 +20,15 @@ namespace rtl::dispatch { using voidfn_t = void(*)(signature_ts...); - template - decltype(auto) get(std::size_t returnId) const + template + constexpr decltype(auto) return_t() const { - using fptr_t = return_t(*)(signature_ts...); - if (returnId == m_returnId) - { - return reinterpret_cast(m_functor); - } - return static_cast(nullptr); + using fptr_t = ret_t(*)(signature_ts...); + return reinterpret_cast(m_functor); } template - bool is_same(return_t(*fptr)(signature_ts...)) const + constexpr bool is_same(return_t(*fptr)(signature_ts...)) const { return (m_functor == reinterpret_cast(fptr)); } diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h new file mode 100644 index 00000000..07a81a21 --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -0,0 +1,60 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "rtl_traits.h" +#include "rtl_typeid.h" +#include "rtl_constants.h" +#include "forward_decls.h" + + +namespace rtl::dispatch +{ + struct functor + { + constexpr void set_lambda(const lambda_hop* lambda) const + { + m_lambda = lambda; + } + + template + constexpr const function_ptr& args_t() const + { + return *(static_cast*>(this)); + } + + template + constexpr const const_method_ptr& get_const() const + { + return *(static_cast*>(this)); + } + + template + constexpr const method_ptr& get_nonconst() const + { + return *(static_cast*>(this)); + } + + GETTER(std::size_t, ReturnId, m_returnId); + GETTER(std::size_t, RecordId, m_recordId); + GETTER(std::size_t, SignatureId, m_signatureId); + +// protected: + + mutable const lambda_hop* m_lambda = nullptr; + + std::size_t m_recordId = detail::TypeId<>::None; + std::size_t m_returnId = detail::TypeId<>::None; + std::size_t m_signatureId = detail::TypeId<>::None; + detail::methodQ m_qualifier = detail::methodQ::None; + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper.h b/ReflectionTemplateLib/rtl/dispatch/hopper.h index 7e08e20d..0c75f21f 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper.h @@ -18,20 +18,19 @@ namespace rtl::dispatch { - template struct hopper { - template requires (std::is_same_v == false) - static decltype(auto) dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept + template //requires (std::is_same_v == false) + static decltype(auto) dispatch(const lambda_hop& lambda_ref, params_t&&...params) noexcept { - auto functor = lambda_ref.get_functor().template get() - .template get(lambda_ref.m_returnId); + auto functor = lambda_ref.get_functor().template args_t...>() + .template return_t>(); - if constexpr (std::is_same_v) { - (*functor)(params...); + if constexpr (std::is_same_v) { + (*functor)(std::forward(params)...); } else { - return (*functor)(params...); + return (*functor)(std::forward(params)...); } } diff --git a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h similarity index 61% rename from ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h rename to ReflectionTemplateLib/rtl/dispatch/lambda_hop.h index 413cf06f..7dc2b79d 100644 --- a/ReflectionTemplateLib/rtl/dispatch/dispatch_interface.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h @@ -18,80 +18,38 @@ #include "rtl_constants.h" #include "forward_decls.h" - -namespace rtl::dispatch -{ - struct lambda_hop; - - struct functor - { - void set_lambda(const lambda_hop* lambda) const - { - m_lambda = lambda; - } - - template - const function_ptr& get() const - { - return *(static_cast*>(this)); - } - - template - const const_method_ptr& get_const() const - { - return *(static_cast*>(this)); - } - - template - const method_ptr& get_nonconst() const - { - return *(static_cast*>(this)); - } - -// protected: - - mutable const lambda_hop* m_lambda = nullptr; - - std::size_t m_recordId = detail::TypeId<>::None; - std::size_t m_returnId = detail::TypeId<>::None; - std::size_t m_signatureId = detail::TypeId<>::None; - detail::methodQ m_qualifier = detail::methodQ::None; - }; -} - - namespace rtl::dispatch { struct lambda_hop { - const functor& get_functor() const + constexpr const functor& get_functor() const { return *m_functor; } template - bool is_member() const + constexpr bool is_member() const { - return (m_recordId == detail::TypeId>::get() || + return (m_recordId == detail::TypeId>::get() || m_recordId == detail::TypeId>::get()); } template - bool is_returning() const + constexpr bool is_returning() const { return (m_returnId == detail::TypeId::get()); } template - bool is_signature() const + constexpr bool is_signature() const { return (m_signatureId == detail::TypeId>::get()); } template - const lambda_hop_function* get_function() const + constexpr const lambda_hop_function* get_function() const { - std::size_t typeId = detail::TypeId>::get(); + const std::size_t typeId = detail::TypeId>::get(); if (typeId == m_signatureId) { return static_cast*>(this); } @@ -109,6 +67,10 @@ namespace rtl::dispatch return nullptr; } + GETTER(std::size_t, ReturnId, m_returnId); + GETTER(std::size_t, RecordId, m_recordId); + GETTER(std::size_t, SignatureId, m_signatureId); + // protected: const functor* m_functor = nullptr; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h index a1615d6f..7cc96cf7 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h @@ -20,7 +20,7 @@ #include "hopper.h" #include "hopper_ctor.h" #include "hopper_const.h" -#include "dispatch_interface.h" +#include "lambda_hop.h" namespace rtl::dispatch { @@ -45,10 +45,11 @@ namespace rtl::dispatch template static lambda_hop_function create(const functor*); - decltype(auto) operator()(const signature_ts&...) const noexcept; + decltype(auto) operator()(signature_ts&&...) const noexcept; + + template + decltype(auto) dispatch(args_t&& ...) const noexcept; - template - decltype(auto) dispatch(const signature_ts&...) const noexcept; template static lambda_hop_function create_method_const(const functor* fptr_hopper) diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp index 8a22e556..9b0a692f 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp @@ -20,26 +20,23 @@ namespace rtl::dispatch inline lambda_hop_function lambda_hop_function::create(const functor* fptr_hopper) { return lambda_hop_function(detail::TypeId::get(), fptr_hopper, nullptr); - //&hopper::template dispatch, return_t>); } - template - inline decltype(auto) lambda_hop_function::operator()(const signature_ts& ...params) const noexcept + template //TODO: static-assert signature_ts == args_t. + inline decltype(auto) lambda_hop_function::operator()(signature_ts&& ...params) const noexcept { - //TODO: static-assert signature_ts == args_t. return m_hopper(*this, params...); } template - template - inline decltype(auto) lambda_hop_function::dispatch(const signature_ts&...params) const noexcept + template //TODO: static-assert signature_ts == args_t. + inline decltype(auto) lambda_hop_function::dispatch(args_t&& ...params) const noexcept { - //TODO: static-assert signature_ts == args_t. if constexpr (std::is_same_v) { - hopper::template dispatch(*this, params...); + hopper::dispatch(*this, std::forward(params)...); } else { - return hopper::template dispatch(*this, params...); + return hopper::dispatch(*this, std::forward(params)...); } } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h index 734ae0de..925cce77 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h @@ -12,7 +12,7 @@ #pragma once //#include "forward_decls.h" -#include "dispatch_interface.h" +#include "lambda_hop.h" #include "hopper_nonconst.h" namespace rtl::dispatch diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp index 2a92ccac..5c8cdc9e 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp @@ -11,8 +11,7 @@ #pragma once -//#include "dispatch_interface.h" - +//#include "functor.h" //#include "lambda_method.h" //#include "hopper_nonconst.h" diff --git a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h index 077d4117..332376e1 100644 --- a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h @@ -13,7 +13,7 @@ #include -#include "dispatch_interface.h" +#include "functor.h" namespace rtl::dispatch { @@ -23,18 +23,14 @@ namespace rtl::dispatch using voidfn_t = void(record_t::*)(signature_ts...); template - decltype(auto) get(std::size_t returnId) const + constexpr decltype(auto) return_t() const { using fptr_t = return_t(record_t::*)(signature_ts...); - if (returnId == m_returnId) - { - return reinterpret_cast(m_functor); - } - return static_cast(nullptr); + return reinterpret_cast(m_functor); } template - bool is_same(return_t(record_t::* fptr)(signature_ts...)) const + constexpr bool is_same(return_t(record_t::* fptr)(signature_ts...)) const { return (m_functor == reinterpret_cast(fptr)); } diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 67c7f702..a4a4e9b6 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -18,6 +18,7 @@ #include "FunctorId.h" #include "rtl_constants.h" #include "FunctionCaller.h" +#include "lambda_hop_function.h" namespace rtl { @@ -94,6 +95,9 @@ namespace rtl { template bool hasSignature() const; + template + const dispatch::lambda_hop_function<_signature...>* lambda_hop(std::size_t pOverloadIndex = 0) const; + template Return operator()(_args&&...params) const noexcept; diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index b16039de..cf8f230b 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -22,6 +22,16 @@ namespace rtl return detail::FunctionCaller<_signature...>{ this }; } + template + const dispatch::lambda_hop_function<_signature...>* Function::lambda_hop(std::size_t pOverloadIndex) const + { + if (pOverloadIndex < m_functorIds.size()) + { + return m_functorIds[pOverloadIndex].m_lambda->get_function<_signature...>(); + } + return nullptr; + } + /* @method: hasSignature<...>() @param: set of arguments, explicitly specified as template parameter. @return: bool, if the functor associated with this object is of certain signature or not. diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index 60d26ca7..d6394d03 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -16,6 +16,7 @@ #include "RObject.h" #include "Function.h" #include "MethodInvoker.h" +#include "lambda_hop_method.h" namespace rtl { @@ -65,6 +66,9 @@ namespace rtl { template const detail::NonConstInvoker<_signature...> bind(constCast&& pTarget) const; + template + const dispatch::lambda_hop_method<_recordType, _signature...>* lambda_hop(std::size_t pOverloadIndex = 0) const; + /* @method: operator()() @return: lambda * accepts no arguments for 'target', since associated functor is static-member-functions. diff --git a/ReflectionTemplateLib/rtl/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp index dcff5e13..86517622 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.hpp +++ b/ReflectionTemplateLib/rtl/inc/Method.hpp @@ -29,6 +29,18 @@ namespace rtl } + template + const dispatch::lambda_hop_method<_recordType, _signature...>* Method::lambda_hop(std::size_t pOverloadIndex) const + { + auto& functorIds = getOverloads(); + if (pOverloadIndex < functorIds.size()) + { + return functorIds[pOverloadIndex].m_lambda->get_method<_recordType, _signature...>(); + } + return nullptr; + } + + /* @method: invokeCtor() @params: variable arguments. @return: RStatus From 0e7fc8b4b1001a92b531aef5e914bf1b42f0e4d0 Mon Sep 17 00:00:00 2001 From: neeraj Date: Sat, 20 Sep 2025 20:52:33 +0530 Subject: [PATCH 18/58] clang/gcc compile error fix. --- .../rtl/dispatch/const_method_ptr.h | 4 ++-- .../rtl/dispatch/hopper_nonconst.h | 24 +++++++++---------- .../rtl/dispatch/method_ptr.h | 4 ++-- 3 files changed, 16 insertions(+), 16 deletions(-) diff --git a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h index 04cad3cc..c5d71095 100644 --- a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h @@ -22,10 +22,10 @@ namespace rtl::dispatch { using voidfn_t = void(record_t::*)(signature_ts...) const; - template + template constexpr decltype(auto) return_t() const { - using fptr_t = return_t(record_t::*)(signature_ts...); + using fptr_t = ret_t(record_t::*)(signature_ts...); return reinterpret_cast(m_functor); } diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h index d5f8c978..08da2b17 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h @@ -21,19 +21,19 @@ namespace rtl::dispatch template struct hopper_nonconst { - template requires (std::is_same_v == false) - static decltype(auto) dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept - { - auto functor = lambda_ref.get_functor().template get_nonconst() - .template get(lambda_ref.m_returnId); + // template requires (std::is_same_v == false) + // static decltype(auto) dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept + // { + // auto functor = lambda_ref.get_functor().template get_nonconst() + // .template get(lambda_ref.m_returnId); - if constexpr (std::is_same_v) { - (target.*functor)(params...); - } - else { - return (target.*functor)(params...); - } - } + // if constexpr (std::is_same_v) { + // (target.*functor)(params...); + // } + // else { + // return (target.*functor)(params...); + // } + // } // template requires (void_t == true) diff --git a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h index 332376e1..72383eff 100644 --- a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h @@ -22,10 +22,10 @@ namespace rtl::dispatch { using voidfn_t = void(record_t::*)(signature_ts...); - template + template constexpr decltype(auto) return_t() const { - using fptr_t = return_t(record_t::*)(signature_ts...); + using fptr_t = ret_t(record_t::*)(signature_ts...); return reinterpret_cast(m_functor); } From ed06e75b40ad622550e7a941a29fafe87b44a774 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Sun, 21 Sep 2025 03:04:35 +0530 Subject: [PATCH 19/58] removed unnecessory reinterpret_cast, code refined. --- .../src/ReflectedCallKnownReturn.cpp | 17 +++--- .../src/ReflectedCallUnknownReturn.cpp | 34 ++++++------ .../rtl/builder/SetupFunction.hpp | 12 +++-- .../rtl/builder/SetupMethod.hpp | 20 +++---- .../rtl/cache/cache_const_method_ptr.h | 15 ++---- .../rtl/cache/cache_function_ptr.h | 15 ++---- .../rtl/cache/cache_lambda_hop_function.h | 4 +- .../rtl/cache/cache_lambda_hop_method.h | 5 +- .../rtl/cache/cache_method_ptr.h | 14 ++--- .../rtl/detail/inc/forward_decls.h | 14 ++--- .../rtl/dispatch/const_method_ptr.h | 23 ++++---- .../rtl/dispatch/function_ptr.h | 27 +++++----- ReflectionTemplateLib/rtl/dispatch/functor.h | 36 +++++++------ ReflectionTemplateLib/rtl/dispatch/hopper.h | 52 +------------------ .../rtl/dispatch/lambda_hop.h | 28 +++++----- .../rtl/dispatch/lambda_hop_function.h | 41 ++------------- .../rtl/dispatch/lambda_hop_function.hpp | 28 +++++----- .../rtl/dispatch/lambda_hop_method.h | 28 ++-------- .../rtl/dispatch/lambda_hop_method.hpp | 29 ----------- .../rtl/dispatch/method_ptr.h | 24 ++++----- 20 files changed, 161 insertions(+), 305 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index f8f06598..3fae81fa 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -102,15 +102,20 @@ namespace void FunctionPointerCall::set(benchmark::State& state) { - static auto passed = _test0(); + static auto* functor = []() -> void(*)(bm::argStr_t) + { + // Must be checked: Passing an incorrect argument or return type is undefined behaviour. + if (sendMessage_lambda.is_returning() && sendMessage_lambda.is_signature()) + { + // No validation is performed internally and the function will not return nullptr on mismatch. + return sendMessage_lambda.return_type().signature().f_ptr(); + } + return nullptr; + }(); - // Unchecked: Passing an incorrect signature or return type is undefined behaviour. - // No validation is performed and the function will not return nullptr on mismatch. - static auto functor = sendMessage_lambda.get_functor().template args_t() - .template return_t(); for (auto _ : state) { - if (passed) + if (functor) { (*functor)(bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index 34f7fb43..d669541f 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -12,30 +12,32 @@ namespace cxx namespace { - static rtl::Function GetMessage; - static rtl::Function SendMessage; - - static rtl::Method NodeGetMessage; - static rtl::Method NodeSendMessage; - - static rtl::RObject nodeObj = []() + static rtl::Function GetMessage = []() { - GetMessage = cxx::mirror().getFunction("getMessage").value(); - - SendMessage = cxx::mirror().getFunction("sendMessage").value(); - - rtl::Record Node = cxx::mirror().getRecord("Node").value(); + return *(cxx::mirror().getFunction("getMessage")); + }(); - NodeGetMessage = Node.getMethod("getMessage").value(); + static rtl::Function SendMessage = []() + { + return *(cxx::mirror().getFunction("sendMessage")); + }(); - NodeSendMessage = Node.getMethod("sendMessage").value(); + static rtl::Method NodeGetMessage = []() + { + return *(cxx::mirror().getRecord("Node")->getMethod("getMessage")); + }(); - auto [err, robj] = Node.create(); + static rtl::Method NodeSendMessage = []() + { + return *(cxx::mirror().getRecord("Node")->getMethod("sendMessage")); + }(); + static const rtl::RObject nodeObj = []() + { + auto [err, robj] = cxx::mirror().getRecord("Node")->create(); if (robj.isEmpty()) { std::cout << "[0] error: " << rtl::to_string(err) << "\n"; } - return std::move(robj); }(); } diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index 65479e5d..2300e812 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -95,16 +95,18 @@ namespace rtl const auto& updateIndex = [&](std::size_t pIndex)-> void { auto& lambdaCache = cache::lambda_hop_function<_signature...>::instance(); - auto& functorCache = cache::function_ptr<_signature...>::instance(); - auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambda = lambdaCache.template push<_returnType>(functor); + auto& functorCache = cache::function_ptr<_returnType, _signature...>::instance(); + + auto* functor = functorCache.push(pFunctor, pIndex); + auto& lambda = lambdaCache.push(functor); + lambdaPtr = λ }; const auto& getIndex = [&]()-> std::size_t { - auto& functorCache = cache::function_ptr<_signature...>::instance(); - auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); + auto& functorCache = cache::function_ptr<_returnType, _signature...>::instance(); + auto [functor, lambdaIndex] = functorCache.find(pFunctor); if (lambdaIndex != rtl::index_none) { lambdaPtr = functor->m_lambda; } diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 424d0361..e82e1b7d 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -166,19 +166,19 @@ namespace rtl::detail const dispatch::lambda_hop* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& functorCache = cache::method_ptr<_recordType, _signature...>::instance(); auto& lambdaCache = cache::lambda_hop_method<_recordType, _signature...>::instance(); + auto& functorCache = cache::method_ptr<_recordType, _returnType, _signature...>::instance(); - auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambda = lambdaCache.template push<_returnType>(functor); + auto* functor = functorCache.push(pFunctor, pIndex); + auto& lambda = lambdaCache.push(functor); lambdaPtr = λ }; const auto& getIndex = [&]()-> std::size_t { - auto& functorCache = cache::method_ptr<_recordType, _signature...>::instance(); - auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); + auto& functorCache = cache::method_ptr<_recordType, _returnType, _signature...>::instance(); + auto [functor, lambdaIndex] = functorCache.find(pFunctor); if (lambdaIndex != rtl::index_none) { lambdaPtr = functor->m_lambda; @@ -238,18 +238,18 @@ namespace rtl::detail const auto& updateIndex = [&](std::size_t pIndex)-> void { auto& lambdaCache = cache::lambda_hop_method<_recordType, _signature...>::instance(); - auto& functorCache = cache::const_method_ptr<_recordType, _signature...>::instance(); + auto& functorCache = cache::const_method_ptr<_recordType, _returnType, _signature...>::instance(); - auto* functor = functorCache.template push<_returnType>(pFunctor, pIndex); - auto& lambda = lambdaCache.template push<_returnType>(functor); + auto* functor = functorCache.push(pFunctor, pIndex); + auto& lambda = lambdaCache.push(functor); lambdaPtr = λ }; const auto& getIndex = [&]()-> std::size_t { - auto& functorCache = cache::const_method_ptr<_recordType, _signature...>::instance(); - auto [functor, lambdaIndex] = functorCache.template find<_returnType>(pFunctor); + auto& functorCache = cache::const_method_ptr<_recordType, _returnType, _signature...>::instance(); + auto [functor, lambdaIndex] = functorCache.find(pFunctor); if (lambdaIndex != rtl::index_none) { lambdaPtr = functor->m_lambda; diff --git a/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h index 163bbffa..94ce76a0 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h @@ -17,34 +17,29 @@ namespace rtl::cache { - template + template struct const_method_ptr { - using functor_t = dispatch::const_method_ptr; + using functor_t = dispatch::const_method_ptr; static const const_method_ptr& instance() { - static const_method_ptr instance_; + static const const_method_ptr instance_; return instance_; } - template const dispatch::functor* push(return_t(record_t::* fptr)(signature_ts...) const, std::size_t lambda_index) const { - using voidfn_t = typename dispatch::const_method_ptr::voidfn_t; - auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); - m_cache.emplace_back(std::make_pair(functor, lambda_index)); + m_cache.emplace_back(std::make_pair(fptr, lambda_index)); return &(m_cache.back().first); - } - template std::pair find(return_t(record_t::* fptr)(signature_ts...) const) const { for (auto& itr : m_cache) { const auto& functor = itr.first; - if (functor.template is_same(fptr)) { + if (functor.is_same(fptr)) { return { &itr.first, itr.second }; } } diff --git a/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h index 5552fc0a..2337eee7 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h @@ -17,10 +17,10 @@ namespace rtl::cache { - template + template struct function_ptr { - using functor_t = dispatch::function_ptr; + using functor_t = dispatch::function_ptr; static const function_ptr& instance() { @@ -28,23 +28,18 @@ namespace rtl::cache return instance_; } - template const dispatch::functor* push(return_t(*fptr)(signature_ts...), std::size_t lambda_index) const { - using voidfn_t = typename dispatch::function_ptr::voidfn_t; - - auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); - m_cache.emplace_back(std::make_pair(functor , lambda_index)); + m_cache.emplace_back(std::make_pair(fptr, lambda_index)); return &(m_cache.back().first); } - template std::pair find(return_t(*fptr)(signature_ts...)) const { for (auto& itr : m_cache) { const auto& functor = itr.first; - if (functor.template is_same(fptr)) { + if (functor.is_same(fptr)) { return { &itr.first, itr.second }; } } @@ -61,6 +56,6 @@ namespace rtl::cache // No reallocation occurs; original objects stay intact mutable std::list> m_cache; - function_ptr() {} + function_ptr() = default; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h index ffc6109d..b27274e5 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h @@ -26,11 +26,9 @@ namespace rtl::cache return instance_; } - template const dispatch::lambda_hop_function& push(const dispatch::functor* fptr) const { - auto lambda = dispatch::lambda_hop_function::template create(fptr); - m_cache.push_back(lambda); + m_cache.push_back(dispatch::lambda_hop_function(fptr)); fptr->set_lambda(&m_cache.back()); return m_cache.back(); } diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h index a2e02f64..f72bc546 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h @@ -15,7 +15,6 @@ #include "lambda_hop_method.h" - namespace rtl::cache { template @@ -27,11 +26,9 @@ namespace rtl::cache return instance_; } - template const dispatch::lambda_hop_method& push(const dispatch::functor* fptr) const { - auto lambda = dispatch::lambda_hop_method::template create(fptr); - m_cache.push_back(lambda); + m_cache.push_back(dispatch::lambda_hop_method(fptr)); fptr->set_lambda(&m_cache.back()); return m_cache.back(); } diff --git a/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h index 05e63d2a..16c19862 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h @@ -17,10 +17,10 @@ namespace rtl::cache { - template + template struct method_ptr { - using functor_t = dispatch::method_ptr; + using functor_t = dispatch::method_ptr; static const method_ptr& instance() { @@ -28,22 +28,18 @@ namespace rtl::cache return instance_; } - template const dispatch::functor* push(return_t(record_t::* fptr)(signature_ts...), std::size_t lambda_index) const { - using voidfn_t = typename dispatch::method_ptr::voidfn_t; - auto functor = functor_t(reinterpret_cast(fptr), detail::TypeId::get()); - m_cache.emplace_back(std::make_pair(functor, lambda_index)); + m_cache.emplace_back(std::make_pair(fptr, lambda_index)); return &(m_cache.back().first); } - template std::pair find(return_t(record_t::* fptr)(signature_ts...)) const { for (auto& itr : m_cache) { const auto& functor = itr.first; - if (functor.template is_same(fptr)) { + if (functor.is_same(fptr)) { return { &itr.first, itr.second }; } } @@ -60,6 +56,6 @@ namespace rtl::cache // No reallocation occurs; original objects stay intact mutable std::list> m_cache; - method_ptr() {} + method_ptr() = default; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index 16317a9a..0497b75d 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -40,18 +40,18 @@ namespace rtl class lambda_hop; template - class lambda_hop_function; + struct lambda_hop_function; template - class lambda_hop_method; + struct lambda_hop_method; - template + template struct function_ptr; - template - struct const_method_ptr; - - template + template struct method_ptr; + + template + struct const_method_ptr; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h index c5d71095..e555d72f 100644 --- a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h @@ -17,32 +17,29 @@ namespace rtl::dispatch { - template + template struct const_method_ptr : public functor { - using voidfn_t = void(record_t::*)(signature_ts...) const; + using functor_t = return_t(record_t::*)(signature_ts...) const; - template - constexpr decltype(auto) return_t() const + constexpr functor_t get() const { - using fptr_t = ret_t(record_t::*)(signature_ts...); - return reinterpret_cast(m_functor); + return m_functor; } - template - constexpr bool is_same(return_t(record_t::*fptr)(signature_ts...) const) const + constexpr bool is_same(functor_t fptr) const { - return (m_functor == reinterpret_cast(fptr)); + return (fptr == m_functor); } - const_method_ptr(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) + const_method_ptr(functor_t fptr) :m_functor(fptr) { - m_returnId = returnId; - m_signatureId = detail::TypeId>::get(); + m_returnId = detail::TypeId>::get(); + m_signatureId = detail::TypeId...>>::get(); } private: - const voidfn_t m_functor; + const functor_t m_functor; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/function_ptr.h b/ReflectionTemplateLib/rtl/dispatch/function_ptr.h index 2fe0b843..fcf92c5d 100644 --- a/ReflectionTemplateLib/rtl/dispatch/function_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/function_ptr.h @@ -11,38 +11,35 @@ #pragma once +#include + #include "functor.h" namespace rtl::dispatch { - template + template struct function_ptr: public functor { - using voidfn_t = void(*)(signature_ts...); + using functor_t = return_t(*)(signature_ts...); - template - constexpr decltype(auto) return_t() const + constexpr functor_t f_ptr() const { - using fptr_t = ret_t(*)(signature_ts...); - return reinterpret_cast(m_functor); + return m_functor; } - template - constexpr bool is_same(return_t(*fptr)(signature_ts...)) const + constexpr bool is_same(functor_t fptr) const { - return (m_functor == reinterpret_cast(fptr)); + return (fptr == m_functor); } - function_ptr(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) + function_ptr(functor_t fptr) :m_functor(fptr) { - m_returnId = returnId; - m_signatureId = detail::TypeId>::get(); + m_returnId = detail::TypeId>::get(); + m_signatureId = detail::TypeId...>>::get(); } - function_ptr(const function_ptr&) = default; - private: - const voidfn_t m_functor; + const functor_t m_functor; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index 07a81a21..1f99015a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -19,30 +19,36 @@ namespace rtl::dispatch { - struct functor + template + struct functor_cast { - constexpr void set_lambda(const lambda_hop* lambda) const - { - m_lambda = lambda; - } + const functor* m_functor; template - constexpr const function_ptr& args_t() const + constexpr const function_ptr& signature() const { - return *(static_cast*>(this)); + return *(static_cast*>(m_functor)); } + }; - template - constexpr const const_method_ptr& get_const() const + struct functor + { + constexpr void set_lambda(const lambda_hop* lambda) const { - return *(static_cast*>(this)); + m_lambda = lambda; } - template - constexpr const method_ptr& get_nonconst() const - { - return *(static_cast*>(this)); - } + //template + //constexpr const const_method_ptr& get_const() const + //{ + // return *(static_cast*>(this)); + //} + + //template + //constexpr const method_ptr& get_nonconst() const + //{ + // return *(static_cast*>(this)); + //} GETTER(std::size_t, ReturnId, m_returnId); GETTER(std::size_t, RecordId, m_recordId); diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper.h b/ReflectionTemplateLib/rtl/dispatch/hopper.h index 0c75f21f..005eec92 100644 --- a/ReflectionTemplateLib/rtl/dispatch/hopper.h +++ b/ReflectionTemplateLib/rtl/dispatch/hopper.h @@ -20,59 +20,9 @@ namespace rtl::dispatch { struct hopper { - template //requires (std::is_same_v == false) + template static decltype(auto) dispatch(const lambda_hop& lambda_ref, params_t&&...params) noexcept { - auto functor = lambda_ref.get_functor().template args_t...>() - .template return_t>(); - - if constexpr (std::is_same_v) { - (*functor)(std::forward(params)...); - } - else { - return (*functor)(std::forward(params)...); - } } - - - // template requires (void_t == true) - // static Return dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept - // { - // if constexpr (std::is_same_v) - // { - // auto functor = lambda_ref.functor().template get() - // .template get(lambda_ref.m_returnId); - - // (*functor)(params...); - // } - // else - // { - // static_assert("return-type mismatch."); - // } - // return { error::None, RObject{} }; - // } - - - // template requires (void_t == false) - // static Return dispatch(const lambda_hop& lambda_ref, const signature_ts&...params) noexcept - // { - // constexpr bool isConstCastSafe = (!traits::is_const_v); - - // auto functor = lambda_ref.functor().template get() - // .template get(lambda_ref.m_returnId); - - // if constexpr (std::is_reference_v) - // { - // using T = traits::raw_t; - // const T& retObj = (*functor)(params...); - // return { error::None, RObject{} }; - // } - // else { - - // auto&& retObj = (*functor)(params...); - // using T = std::remove_cvref_t; - // return { error::None, RObject{} }; - // } - // } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h index 7dc2b79d..2e249d9a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h @@ -17,40 +17,43 @@ #include "rtl_typeid.h" #include "rtl_constants.h" #include "forward_decls.h" +#include "functor.h" namespace rtl::dispatch { struct lambda_hop { - constexpr const functor& get_functor() const + template + constexpr const functor_cast return_type() const { - return *m_functor; + return functor_cast{ m_functor }; } template constexpr bool is_member() const { - return (m_recordId == detail::TypeId>::get() || - m_recordId == detail::TypeId>::get()); + return (m_functor->m_recordId == detail::TypeId>::get() || + m_functor->m_recordId == detail::TypeId>::get()); } template constexpr bool is_returning() const { - return (m_returnId == detail::TypeId::get()); + return (m_functor->m_returnId == detail::TypeId>::get()); } template constexpr bool is_signature() const { - return (m_signatureId == detail::TypeId>::get()); + return (m_signatureId == detail::TypeId...>>::get()); } template constexpr const lambda_hop_function* get_function() const { - const std::size_t typeId = detail::TypeId>::get(); - if (typeId == m_signatureId) { + const std::size_t typeId = detail::TypeId...>>::get(); + if (typeId == m_signatureId) + { return static_cast*>(this); } return nullptr; @@ -60,22 +63,19 @@ namespace rtl::dispatch const lambda_hop_method* get_method() const { std::size_t recordId = detail::TypeId::get(); - std::size_t typeId = detail::TypeId>::get(); - if (typeId == m_signatureId && recordId == m_recordId) { + std::size_t typeId = detail::TypeId...>>::get(); + if (typeId == m_signatureId && recordId == m_functor->m_recordId) + { return static_cast*>(this); } return nullptr; } - GETTER(std::size_t, ReturnId, m_returnId); - GETTER(std::size_t, RecordId, m_recordId); GETTER(std::size_t, SignatureId, m_signatureId); // protected: const functor* m_functor = nullptr; - std::size_t m_recordId = detail::TypeId<>::None; - std::size_t m_returnId = detail::TypeId<>::None; std::size_t m_signatureId = detail::TypeId<>::None; std::vector m_argumentsId = {}; }; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h index 7cc96cf7..06aff442 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h @@ -11,51 +11,16 @@ #pragma once -#include -#include -#include - -#include "forward_decls.h" - -#include "hopper.h" -#include "hopper_ctor.h" -#include "hopper_const.h" #include "lambda_hop.h" namespace rtl::dispatch { template - class lambda_hop_function: public lambda_hop + struct lambda_hop_function: public lambda_hop { - using lambda_t = std::function; - - const lambda_t m_hopper; - - lambda_hop_function(std::size_t returnId, const functor* functor, lambda_t hopper) noexcept - : m_hopper(std::move(hopper)) - { - m_functor = functor; - m_returnId = returnId; - m_signatureId = detail::TypeId>::get(); - detail::TypeId::get(m_argumentsId); - } - - public: - - template - static lambda_hop_function create(const functor*); - - decltype(auto) operator()(signature_ts&&...) const noexcept; + lambda_hop_function(const functor*) noexcept; template - decltype(auto) dispatch(args_t&& ...) const noexcept; - - - template - static lambda_hop_function create_method_const(const functor* fptr_hopper) - { - return lambda(detail::TypeId::get(), fptr_hopper, nullptr); - //&hopper_const::template dispatch); - } + decltype(auto) dispatch(args_t&&...) const noexcept; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp index 9b0a692f..d17581ab 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp @@ -11,32 +11,36 @@ #pragma once +#include "rtl_typeid.h" #include "lambda_hop_function.h" namespace rtl::dispatch { template - template - inline lambda_hop_function lambda_hop_function::create(const functor* fptr_hopper) + inline lambda_hop_function::lambda_hop_function(const functor* functor) noexcept { - return lambda_hop_function(detail::TypeId::get(), fptr_hopper, nullptr); + m_functor = functor; + m_signatureId = detail::TypeId...>>::get(); + detail::TypeId::get(m_argumentsId); } - template //TODO: static-assert signature_ts == args_t. - inline decltype(auto) lambda_hop_function::operator()(signature_ts&& ...params) const noexcept - { - return m_hopper(*this, params...); - } template - template //TODO: static-assert signature_ts == args_t. + template inline decltype(auto) lambda_hop_function::dispatch(args_t&& ...params) const noexcept { - if constexpr (std::is_same_v) { - hopper::dispatch(*this, std::forward(params)...); + constexpr bool signature_ok = std::is_same_v< std::tuple...>, + std::tuple>; + + static_assert( signature_ok, "Argument types don’t match signature."); + + auto* functor = return_type>().template signature...>().f_ptr(); + + if constexpr (std::is_same_v) { + (*functor)(std::forward(params)...); } else { - return hopper::dispatch(*this, std::forward(params)...); + return (*functor)(std::forward(params)...); } } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h index 925cce77..f193d720 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h @@ -11,43 +11,21 @@ #pragma once -//#include "forward_decls.h" #include "lambda_hop.h" #include "hopper_nonconst.h" namespace rtl::dispatch { template - class lambda_hop_method : public lambda_hop + struct lambda_hop_method : public lambda_hop { - using lambda_t = std::function; - - const lambda_t m_hopper; - - lambda_hop_method(std::size_t returnId, const functor* functor, lambda_t hopper) noexcept - : m_hopper(std::move(hopper)) + lambda_hop_method(const functor* functor) noexcept { m_functor = functor; - m_returnId = returnId; - m_recordId = detail::TypeId::get(); - m_signatureId = detail::TypeId>::get(); + m_signatureId = detail::TypeId...>>::get(); detail::TypeId::get(m_argumentsId); } - public: - - template - static lambda_hop_method create(const functor* fptr_hopper) - { - return lambda_hop_method(detail::TypeId::get(), fptr_hopper, nullptr); - //&hopper_nonconst::template dispatch, return_t>); - } - - decltype(auto) operator()(record_t& target, const signature_ts& ...params) const noexcept - { - return m_hopper(target, *this, params...); - } - template decltype(auto) dispatch(record_t& target, const signature_ts& ...params) const noexcept { diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp index 5c8cdc9e..3b1a16c9 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp @@ -18,33 +18,4 @@ namespace rtl::detail { - //template - //template - //inline lambda_method lambda_method::create(const functor* fptr_hopper) - //{ - // return lambda_method(); - // //lambda_method(detail::TypeId::get(), fptr_hopper, - // // &hopper_nonconst::template dispatch, return_t>); - //} - - - //template - //inline decltype(auto) lambda_method::operator()(record_t& target, const signature_ts& ...params) const noexcept - //{ - // //TODO: static-assert signature_ts == args_t && enable perfect-forwarding - // return m_hopper(target, *this, params...); - //} - - - // template - // template - // inline return_t lambda_method::dispatch(record_t& target, const signature_ts&...params) const noexcept - // { - // if constexpr (std::is_same_v) { - // hopper_nonconst::template dispatch(target, *this, params...); - // } - // else { - // return hopper_nonconst::template dispatch(target, *this, params...); - // } - // } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h index 72383eff..403afeae 100644 --- a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h @@ -17,32 +17,30 @@ namespace rtl::dispatch { - template + template struct method_ptr : public functor { - using voidfn_t = void(record_t::*)(signature_ts...); + using functor_t = return_t(record_t::*)(signature_ts...); - template - constexpr decltype(auto) return_t() const + constexpr functor_t get() const { - using fptr_t = ret_t(record_t::*)(signature_ts...); - return reinterpret_cast(m_functor); + return m_functor; } - template - constexpr bool is_same(return_t(record_t::* fptr)(signature_ts...)) const + constexpr bool is_same(functor_t fptr) const { - return (m_functor == reinterpret_cast(fptr)); + return (fptr == m_functor); } - method_ptr(voidfn_t fptr, std::size_t returnId) :m_functor(fptr) + method_ptr(functor_t fptr) :m_functor(fptr) { - m_returnId = returnId; - m_signatureId = detail::TypeId>::get(); + m_recordId = detail::TypeId>::get(); + m_returnId = detail::TypeId>::get(); + m_signatureId = detail::TypeId...>>::get(); } private: - const voidfn_t m_functor; + const functor_t m_functor; }; } \ No newline at end of file From dca661d685f9bde7f60f27b252550aa7ade0aab0 Mon Sep 17 00:00:00 2001 From: neeraj Date: Sun, 21 Sep 2025 03:12:28 +0530 Subject: [PATCH 20/58] unicode-char from comment removed. --- ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp index d17581ab..e1fd291a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp @@ -32,7 +32,7 @@ namespace rtl::dispatch constexpr bool signature_ok = std::is_same_v< std::tuple...>, std::tuple>; - static_assert( signature_ok, "Argument types don’t match signature."); + static_assert( signature_ok, "Argument types don't match signature."); auto* functor = return_type>().template signature...>().f_ptr(); From 8610277a2fbb61de2e618a09878aa6460c06ba6a Mon Sep 17 00:00:00 2001 From: neeraj Date: Sun, 21 Sep 2025 13:58:15 +0530 Subject: [PATCH 21/58] benchmark for method-call with known return added. --- .../src/ReflectedCallKnownReturn.cpp | 142 ++++++++++++------ .../src/ReflectedCallKnownReturn.h | 2 +- .../src/ReflectedCallUnknownReturn.cpp | 2 +- RTLBenchmarkApp/src/main.cpp | 6 +- .../rtl/builder/SetupFunction.hpp | 7 +- .../rtl/builder/SetupMethod.hpp | 12 +- .../rtl/detail/inc/CMakeLists.txt | 5 + .../{dispatch => detail/inc}/CallReflector.h | 0 .../{dispatch => detail/inc}/FunctionCaller.h | 0 .../inc}/FunctionCaller.hpp | 0 .../{dispatch => detail/inc}/MethodInvoker.h | 0 .../inc}/MethodInvoker.hpp | 0 .../rtl/dispatch/CMakeLists.txt | 13 -- ReflectionTemplateLib/rtl/dispatch/functor.h | 29 +--- ReflectionTemplateLib/rtl/dispatch/hopper.h | 28 ---- .../rtl/dispatch/hopper_const.h | 28 ---- .../rtl/dispatch/hopper_ctor.h | 39 ----- .../rtl/dispatch/hopper_nonconst.h | 79 ---------- .../rtl/dispatch/lambda_hop.h | 15 +- .../rtl/dispatch/lambda_hop_function.h | 39 ++++- .../rtl/dispatch/lambda_hop_function.hpp | 46 ------ .../rtl/dispatch/lambda_hop_method.h | 32 +++- .../rtl/dispatch/lambda_hop_method.hpp | 21 --- .../rtl/dispatch/method_ptr.h | 2 +- 24 files changed, 189 insertions(+), 358 deletions(-) rename ReflectionTemplateLib/rtl/{dispatch => detail/inc}/CallReflector.h (100%) rename ReflectionTemplateLib/rtl/{dispatch => detail/inc}/FunctionCaller.h (100%) rename ReflectionTemplateLib/rtl/{dispatch => detail/inc}/FunctionCaller.hpp (100%) rename ReflectionTemplateLib/rtl/{dispatch => detail/inc}/MethodInvoker.h (100%) rename ReflectionTemplateLib/rtl/{dispatch => detail/inc}/MethodInvoker.hpp (100%) delete mode 100644 ReflectionTemplateLib/rtl/dispatch/hopper.h delete mode 100644 ReflectionTemplateLib/rtl/dispatch/hopper_const.h delete mode 100644 ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h delete mode 100644 ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h delete mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp delete mode 100644 ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 3fae81fa..dd2457ef 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -1,8 +1,6 @@ #include #include -//#include -#include #include "BenchMark.h" #include "ReflectedCallKnownReturn.h" @@ -22,33 +20,32 @@ namespace { static const rtl::lambda_function& getMessage_lambda = []() { + // No validation is performed internally and lambda_hop + // will not return nullptr on signature mismatch. (by design) return *(cxx::mirror().getFunction("getMessage")->lambda_hop()); }(); static const rtl::lambda_function& sendMessage_lambda = []() { + // No validation is performed internally and lambda_hop + // will not return nullptr on signature mismatch. (by design) return *(cxx::mirror().getFunction("sendMessage")->lambda_hop()); }(); static const rtl::lambda_method& getMessageOnNode_lambda = []() { + // No validation is performed internally and lambda_hop + // will not return nullptr on signature mismatch. (by design) return *(cxx::mirror().getRecord("Node")->getMethod("getMessage")->lambda_hop()); }(); static const rtl::lambda_method& sendMessageOnNode_lambda = []() { rtl::Record Node = cxx::mirror().getRecord("Node").value(); + // No validation is performed internally and lambda_hop + // will not return nullptr on signature mismatch. (by design) return *(cxx::mirror().getRecord("Node")->getMethod("sendMessage")->lambda_hop()); }(); - - static const rtl::RObject nodeObj = []() - { - auto [err, robj] = cxx::mirror().getRecord("Node")->create(); - if (robj.isEmpty()) { - std::cout << "[0] error: " << rtl::to_string(err) << "\n"; - } - return std::move(robj); - }(); } @@ -65,38 +62,38 @@ namespace return true; }; - - //static auto _test1 = []() - //{ - // if (sendMessageOnNode_lambda == nullptr) - // { - // std::cout << "[1] error: signature mismatch.\n"; - // return false; - // } - // return true; - //}; - + static auto _test1 = []() + { + if(!sendMessageOnNode_lambda.is_signature() || + !sendMessageOnNode_lambda.is_returning()) + { + std::cout << "[1] error: signature mismatch.\n"; + return false; + } + return true; + }; static auto _test2 = []() { if (!getMessage_lambda.is_signature() || !getMessage_lambda.is_returning()) { - std::cout << "[0] error: signature mismatch.\n"; + std::cout << "[2] error: signature mismatch.\n"; return false; } return true; }; - //static auto _test3 = []() - //{ - // if (getMessageOnNode_lambda == nullptr) - // { - // std::cout << "[3] error: signature mismatch.\n"; - // return false; - // } - // return true; - //}; + static auto _test3 = []() + { + if (!getMessageOnNode_lambda.is_signature() || + !getMessageOnNode_lambda.is_returning()) + { + std::cout << "[3] error: signature mismatch.\n"; + return false; + } + return true; + }; } @@ -108,8 +105,9 @@ void FunctionPointerCall::set(benchmark::State& state) if (sendMessage_lambda.is_returning() && sendMessage_lambda.is_signature()) { // No validation is performed internally and the function will not return nullptr on mismatch. - return sendMessage_lambda.return_type().signature().f_ptr(); + return sendMessage_lambda.get_functor().f_ptr(); } + std::cout << "[4] error: signature mismatch.\n"; return nullptr; }(); @@ -124,6 +122,30 @@ void FunctionPointerCall::set(benchmark::State& state) } +void FunctionPointerCall::get(benchmark::State& state) +{ + static auto* functor = []() -> bm::retStr_t(*)(bm::argStr_t) + { + // Must be checked: Passing an incorrect argument or return type is undefined behaviour. + if (getMessage_lambda.is_returning() && getMessage_lambda.is_signature()) + { + // No validation is performed internally and the function will not return nullptr on mismatch. + return getMessage_lambda.get_functor().f_ptr(); + } + std::cout << "[5] error: signature mismatch.\n"; + return nullptr; + }(); + + for (auto _ : state) + { + if (functor) + { + auto ret = (*functor)(bm::g_longStr); + benchmark::DoNotOptimize(ret); + } + } +} + void ReflectedCallKnownReturn::set(benchmark::State& state) { @@ -155,21 +177,51 @@ void ReflectedCallKnownReturn::get(benchmark::State& state) void ReflectedMethodCallKnownReturn::set(benchmark::State& state) { - //static auto _=_test1(); - //for (auto _: state) - //{ - // auto error = (NodeSendMessage(nodeObj)(bm::g_longStr).err; - // benchmark::DoNotOptimize(error); - //} + static bm::Node nodeObj; + static auto functor = []() -> void(bm::Node::*)(bm::argStr_t) + { + // Must be checked: Passing an incorrect argument or return type is undefined behaviour. + if (sendMessageOnNode_lambda.is_returning() && sendMessageOnNode_lambda.is_signature()) + { + // No validation is performed internally and the function will not return nullptr on mismatch. + return sendMessageOnNode_lambda.get_functor().f_ptr(); + } + std::cout << "[6] error: signature mismatch.\n"; + return nullptr; + }(); + + for (auto _ : state) + { + if (functor) + { + sendMessageOnNode_lambda.dispatch(nodeObj, bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); + } + } } void ReflectedMethodCallKnownReturn::get(benchmark::State& state) { - //static auto _=_test3(); - //for (auto _: state) - //{ - // auto error = NodeGetMessage(nodeObj)(bm::g_longStr).err; - // benchmark::DoNotOptimize(error); - //} + static bm::Node nodeObj; + static auto functor = []() -> bm::retStr_t(bm::Node::*)(bm::argStr_t) + { + // Must be checked: Passing an incorrect argument or return type is undefined behaviour. + if (getMessageOnNode_lambda.is_returning() && getMessageOnNode_lambda.is_signature()) + { + // No validation is performed internally and the function will not return nullptr on mismatch. + return getMessageOnNode_lambda.get_functor().f_ptr(); + } + std::cout << "[7] error: signature mismatch.\n"; + return nullptr; + }(); + + for (auto _ : state) + { + if (functor) + { + auto retStr = getMessageOnNode_lambda.dispatch(nodeObj, bm::g_longStr); + benchmark::DoNotOptimize(retStr); + } + } } \ No newline at end of file diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h index 7084e5fa..eefbd04c 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h @@ -19,7 +19,7 @@ struct FunctionPointerCall struct ReflectedMethodCallKnownReturn -{ +{ static void set(benchmark::State& state); static void get(benchmark::State& state); diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index d669541f..91ca4fb4 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -36,7 +36,7 @@ namespace { auto [err, robj] = cxx::mirror().getRecord("Node")->create(); if (robj.isEmpty()) { - std::cout << "[0] error: " << rtl::to_string(err) << "\n"; + std::cout << "[_] error: " << rtl::to_string(err) << "\n"; } return std::move(robj); }(); diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index c632e469..d459fd79 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -9,6 +9,7 @@ BENCHMARK(NativeCall::set); BENCHMARK(FunctionPointerCall::set); + //BENCHMARK(ReflectedCallKnownReturn::set); //BENCHMARK(ReflectedCallKnownReturn::set); @@ -17,17 +18,18 @@ BENCHMARK(ReflectedCallKnownReturn::set); BENCHMARK(ReflectedCallUnknownReturn::set); BENCHMARK(StdFunctionMethodCall::set); -//BENCHMARK(ReflectedMethodCallKnownReturn::set); +BENCHMARK(ReflectedMethodCallKnownReturn::set); BENCHMARK(ReflectedMethodCallUnknownReturn::set); BENCHMARK(NativeCall::get); +BENCHMARK(FunctionPointerCall::get); BENCHMARK(StdFunctionCall::get); BENCHMARK(ReflectedCallKnownReturn::get); BENCHMARK(ReflectedCallUnknownReturn::get); BENCHMARK(StdFunctionMethodCall::get); -//BENCHMARK(ReflectedMethodCallKnownReturn::get); +BENCHMARK(ReflectedMethodCallKnownReturn::get); BENCHMARK(ReflectedMethodCallUnknownReturn::get); namespace bm diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index 2300e812..a5cc37eb 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -13,7 +13,6 @@ #include -#include "lambda_hop_function.hpp" #include "cache_lambda_hop_function.h" #include "cache_function_ptr.h" @@ -31,7 +30,7 @@ namespace rtl { return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); assert(isAllGood && "new type-id-system not working."); pFunctor(std::forward<_signature>(params)...); @@ -49,7 +48,7 @@ namespace rtl this is stored in _derivedType's (FunctorContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, _signature&&...params)-> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); assert(isAllGood && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); @@ -108,7 +107,7 @@ namespace rtl auto& functorCache = cache::function_ptr<_returnType, _signature...>::instance(); auto [functor, lambdaIndex] = functorCache.find(pFunctor); if (lambdaIndex != rtl::index_none) { - lambdaPtr = functor->m_lambda; + lambdaPtr = functor->getLambdaHop(); } return lambdaIndex; }; diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index e82e1b7d..2d416b8b 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -34,7 +34,7 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); assert(isAllGood && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { @@ -57,7 +57,7 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); assert(isAllGood && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { @@ -101,7 +101,7 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); assert(isAllGood && "new type-id-system not working."); const _recordType& target = pTargetObj.view<_recordType>()->get(); @@ -120,7 +120,7 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->m_lambda); + bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); assert(isAllGood && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); @@ -181,7 +181,7 @@ namespace rtl::detail auto [functor, lambdaIndex] = functorCache.find(pFunctor); if (lambdaIndex != rtl::index_none) { - lambdaPtr = functor->m_lambda; + lambdaPtr = functor->getLambdaHop(); } return lambdaIndex; }; @@ -252,7 +252,7 @@ namespace rtl::detail auto [functor, lambdaIndex] = functorCache.find(pFunctor); if (lambdaIndex != rtl::index_none) { - lambdaPtr = functor->m_lambda; + lambdaPtr = functor->getLambdaHop(); } return lambdaIndex; }; diff --git a/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt b/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt index 343cfb2f..ff6e9609 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt @@ -12,6 +12,11 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/RObjectId.h" "${CMAKE_CURRENT_SOURCE_DIR}/RObjectUPtr.h" "${CMAKE_CURRENT_SOURCE_DIR}/RObjExtracter.h" + "${CMAKE_CURRENT_SOURCE_DIR}/CallReflector.h" + "${CMAKE_CURRENT_SOURCE_DIR}/FunctionCaller.h" + "${CMAKE_CURRENT_SOURCE_DIR}/FunctionCaller.hpp" + "${CMAKE_CURRENT_SOURCE_DIR}/MethodInvoker.h" + "${CMAKE_CURRENT_SOURCE_DIR}/MethodInvoker.hpp" ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/dispatch/CallReflector.h b/ReflectionTemplateLib/rtl/detail/inc/CallReflector.h similarity index 100% rename from ReflectionTemplateLib/rtl/dispatch/CallReflector.h rename to ReflectionTemplateLib/rtl/detail/inc/CallReflector.h diff --git a/ReflectionTemplateLib/rtl/dispatch/FunctionCaller.h b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h similarity index 100% rename from ReflectionTemplateLib/rtl/dispatch/FunctionCaller.h rename to ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h diff --git a/ReflectionTemplateLib/rtl/dispatch/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp similarity index 100% rename from ReflectionTemplateLib/rtl/dispatch/FunctionCaller.hpp rename to ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp diff --git a/ReflectionTemplateLib/rtl/dispatch/MethodInvoker.h b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h similarity index 100% rename from ReflectionTemplateLib/rtl/dispatch/MethodInvoker.h rename to ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h diff --git a/ReflectionTemplateLib/rtl/dispatch/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp similarity index 100% rename from ReflectionTemplateLib/rtl/dispatch/MethodInvoker.hpp rename to ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp diff --git a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt index 3d512652..6be5bbee 100644 --- a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt @@ -10,20 +10,7 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop.h" "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_method.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_method.hpp" "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_function.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_function.hpp" - "${CMAKE_CURRENT_SOURCE_DIR}/hopper.h" - "${CMAKE_CURRENT_SOURCE_DIR}/hopper_ctor.h" - "${CMAKE_CURRENT_SOURCE_DIR}/hopper_const.h" - "${CMAKE_CURRENT_SOURCE_DIR}/hopper_nonconst.h" - - "${CMAKE_CURRENT_SOURCE_DIR}/CallReflector.h" - "${CMAKE_CURRENT_SOURCE_DIR}/FunctionCaller.h" - "${CMAKE_CURRENT_SOURCE_DIR}/FunctionCaller.hpp" - "${CMAKE_CURRENT_SOURCE_DIR}/MethodInvoker.h" - "${CMAKE_CURRENT_SOURCE_DIR}/MethodInvoker.hpp" - ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index 1f99015a..5f8e6152 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -11,26 +11,12 @@ #pragma once -#include "rtl_traits.h" #include "rtl_typeid.h" #include "rtl_constants.h" #include "forward_decls.h" - namespace rtl::dispatch { - template - struct functor_cast - { - const functor* m_functor; - - template - constexpr const function_ptr& signature() const - { - return *(static_cast*>(m_functor)); - } - }; - struct functor { constexpr void set_lambda(const lambda_hop* lambda) const @@ -38,23 +24,12 @@ namespace rtl::dispatch m_lambda = lambda; } - //template - //constexpr const const_method_ptr& get_const() const - //{ - // return *(static_cast*>(this)); - //} - - //template - //constexpr const method_ptr& get_nonconst() const - //{ - // return *(static_cast*>(this)); - //} - GETTER(std::size_t, ReturnId, m_returnId); GETTER(std::size_t, RecordId, m_recordId); GETTER(std::size_t, SignatureId, m_signatureId); + GETTER(lambda_hop*, LambdaHop, m_lambda); -// protected: + protected: mutable const lambda_hop* m_lambda = nullptr; diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper.h b/ReflectionTemplateLib/rtl/dispatch/hopper.h deleted file mode 100644 index 005eec92..00000000 --- a/ReflectionTemplateLib/rtl/dispatch/hopper.h +++ /dev/null @@ -1,28 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include - -#include "lambda_hop_function.h" -#include "function_ptr.h" - -namespace rtl::dispatch -{ - struct hopper - { - template - static decltype(auto) dispatch(const lambda_hop& lambda_ref, params_t&&...params) noexcept - { - } - }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_const.h b/ReflectionTemplateLib/rtl/dispatch/hopper_const.h deleted file mode 100644 index 9134db40..00000000 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_const.h +++ /dev/null @@ -1,28 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -//#include "RObject.h" -//#include "lambda_function.h" - -namespace rtl::dispatch -{ - // template - // struct hopper_const - // { - // template - // static Return dispatch(const lambda_hop&, const signature_ts&...) noexcept - // { - // return { error::EmptyRObject, RObject{} }; - // } - // }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h b/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h deleted file mode 100644 index d058d568..00000000 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_ctor.h +++ /dev/null @@ -1,39 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - - -//#include "lambda_function.h" - -namespace rtl::dispatch -{ - // template - // struct hopper_ctor - // { - // template - // static Return dispatch(const lambda_hop&, const signature_ts&...) noexcept - // { - // return { error::EmptyRObject, RObject{} }; - // } - // }; - - - // template - // struct hopper_copyctor - // { - // template - // static Return dispatch(const lambda_hop&, signature_ts&&...) noexcept - // { - // return { error::EmptyRObject, RObject{} }; - // } - // }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h b/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h deleted file mode 100644 index 08da2b17..00000000 --- a/ReflectionTemplateLib/rtl/dispatch/hopper_nonconst.h +++ /dev/null @@ -1,79 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -//#include "forward_decls.h" - -//#include "lambda_function.h" -//#include "functor.h" - -namespace rtl::dispatch -{ - template - struct hopper_nonconst - { - // template requires (std::is_same_v == false) - // static decltype(auto) dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept - // { - // auto functor = lambda_ref.get_functor().template get_nonconst() - // .template get(lambda_ref.m_returnId); - - // if constexpr (std::is_same_v) { - // (target.*functor)(params...); - // } - // else { - // return (target.*functor)(params...); - // } - // } - - - // template requires (void_t == true) - // static Return dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept - // { - // if constexpr (std::is_same_v) - // { - // auto functor = lambda_ref.functor().template get_nonconst() - // .template get(lambda_ref.m_returnId); - - // (target.*functor)(params...); - // } - // else - // { - // static_assert("return-type mismatch."); - // } - // return { error::None, RObject{} }; - // } - - - // template requires (void_t == false) - // static Return dispatch(record_t& target, const lambda_hop& lambda_ref, const signature_ts&...params) noexcept - // { - // constexpr bool isConstCastSafe = (!traits::is_const_v); - - // auto functor = lambda_ref.functor().template get_nonconst() - // .template get(lambda_ref.m_returnId); - - // if constexpr (std::is_reference_v) - // { - // using T = traits::raw_t; - // const T& retObj = (target.*functor)(params...); - // return { error::None, RObject{} }; - // } - // else { - - // auto&& retObj = (target.*functor)(params...); - // using T = std::remove_cvref_t; - // return { error::None, RObject{} }; - // } - // } - }; -} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h index 2e249d9a..c537db26 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h @@ -16,30 +16,23 @@ #include "rtl_traits.h" #include "rtl_typeid.h" #include "rtl_constants.h" -#include "forward_decls.h" #include "functor.h" namespace rtl::dispatch { struct lambda_hop { - template - constexpr const functor_cast return_type() const - { - return functor_cast{ m_functor }; - } - template constexpr bool is_member() const { - return (m_functor->m_recordId == detail::TypeId>::get() || - m_functor->m_recordId == detail::TypeId>::get()); + return (m_functor->getRecordId() == detail::TypeId>::get() || + m_functor->getRecordId() == detail::TypeId>::get()); } template constexpr bool is_returning() const { - return (m_functor->m_returnId == detail::TypeId>::get()); + return (m_functor->getReturnId() == detail::TypeId>::get()); } template @@ -64,7 +57,7 @@ namespace rtl::dispatch { std::size_t recordId = detail::TypeId::get(); std::size_t typeId = detail::TypeId...>>::get(); - if (typeId == m_signatureId && recordId == m_functor->m_recordId) + if (typeId == m_signatureId && recordId == m_functor->getRecordId()) { return static_cast*>(this); } diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h index 06aff442..4401acd7 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h @@ -12,15 +12,50 @@ #pragma once #include "lambda_hop.h" +#include "function_ptr.h" namespace rtl::dispatch { template struct lambda_hop_function: public lambda_hop { - lambda_hop_function(const functor*) noexcept; + lambda_hop_function(const functor* fptr) noexcept + { + m_functor = fptr; + m_signatureId = detail::TypeId...>>::get(); + detail::TypeId::get(m_argumentsId); + } + + template + constexpr const function_ptr& get_functor() const + { + // Unchecked: using an incorrect argument or return type is undefined behaviour. + // No validation is performed and the function will not return nullptr on mismatch. (By Design) + return *(static_cast*>(m_functor)); + } template - decltype(auto) dispatch(args_t&&...) const noexcept; + constexpr decltype(auto) dispatch(args_t&&...params) const + noexcept(noexcept( + std::invoke(get_functor().f_ptr(),std::declval()...) + )) + { + constexpr bool signature_ok = std::is_same_v< + std::tuple...>, + std::tuple + >; + static_assert( signature_ok, "Argument types don't match signature."); + + using fptr_t = typename function_ptr::functor_t; + + fptr_t functor = get_functor().f_ptr(); + + if constexpr (std::is_same_v) { + (*functor)(std::forward(params)...); + } + else { + return (*functor)(std::forward(params)...); + } + } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp deleted file mode 100644 index e1fd291a..00000000 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.hpp +++ /dev/null @@ -1,46 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -#include "rtl_typeid.h" -#include "lambda_hop_function.h" - -namespace rtl::dispatch -{ - template - inline lambda_hop_function::lambda_hop_function(const functor* functor) noexcept - { - m_functor = functor; - m_signatureId = detail::TypeId...>>::get(); - detail::TypeId::get(m_argumentsId); - } - - - template - template - inline decltype(auto) lambda_hop_function::dispatch(args_t&& ...params) const noexcept - { - constexpr bool signature_ok = std::is_same_v< std::tuple...>, - std::tuple>; - - static_assert( signature_ok, "Argument types don't match signature."); - - auto* functor = return_type>().template signature...>().f_ptr(); - - if constexpr (std::is_same_v) { - (*functor)(std::forward(params)...); - } - else { - return (*functor)(std::forward(params)...); - } - } -} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h index f193d720..a607488c 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h @@ -12,13 +12,17 @@ #pragma once #include "lambda_hop.h" -#include "hopper_nonconst.h" +#include "method_ptr.h" +#include namespace rtl::dispatch { template struct lambda_hop_method : public lambda_hop { + template + using fptr_t = typename method_ptr::functor_t; + lambda_hop_method(const functor* functor) noexcept { m_functor = functor; @@ -27,13 +31,33 @@ namespace rtl::dispatch } template - decltype(auto) dispatch(record_t& target, const signature_ts& ...params) const noexcept + constexpr const method_ptr& get_functor() const { + // Unchecked: using an incorrect argument or return type is undefined behaviour. + // No validation is performed and the function will not return nullptr on mismatch. (By Design) + return *(static_cast*>(m_functor)); + } + + template + constexpr decltype(auto) dispatch(record_t& target, args_t&& ...params) const + noexcept(noexcept( + (std::declval().*std::declval>())(std::declval()...) + )) + { + constexpr bool signature_ok = std::is_same_v< + std::tuple...>, + std::tuple + >; + + static_assert( signature_ok, "Argument types don't match signature."); + + fptr_t functor = get_functor().f_ptr(); + if constexpr (std::is_same_v) { - hopper_nonconst::template dispatch(target, *this, params...); + (target.*functor)(std::forward(params)...); } else { - return hopper_nonconst::template dispatch(target, *this, params...); + return (target.*functor)(std::forward(params)...); } } }; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp deleted file mode 100644 index 3b1a16c9..00000000 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.hpp +++ /dev/null @@ -1,21 +0,0 @@ -/************************************************************************* - * * - * Reflection Template Library (RTL) - Modern C++ Reflection Framework * - * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * - * * - * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * - * * - *************************************************************************/ - - -#pragma once - -//#include "functor.h" -//#include "lambda_method.h" -//#include "hopper_nonconst.h" - -namespace rtl::detail -{ - -} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h index 403afeae..12563781 100644 --- a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h @@ -22,7 +22,7 @@ namespace rtl::dispatch { using functor_t = return_t(record_t::*)(signature_ts...); - constexpr functor_t get() const + constexpr functor_t f_ptr() const { return m_functor; } From fb21c8461b7ce8750dad2e7769aaa4553df6f15b Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Mon, 22 Sep 2025 01:56:11 +0530 Subject: [PATCH 22/58] refactored/refined & tested caches/lambda/functor for correct fptrs. --- .../src/ReflectedCallKnownReturn.cpp | 24 +++---- RTLBenchmarkApp/src/main.cpp | 2 + .../CxxMirrorTests/CxxMirrorObjectTest.cpp | 8 +-- .../rtl/builder/SetupFunction.hpp | 16 ++--- .../rtl/builder/SetupMethod.hpp | 32 ++++----- .../rtl/cache/cache_const_method_ptr.h | 4 +- .../rtl/cache/cache_function_ptr.h | 4 +- .../rtl/cache/cache_lambda_hop_function.h | 24 +++---- .../rtl/cache/cache_lambda_hop_method.h | 24 +++---- .../rtl/cache/cache_method_ptr.h | 4 +- .../rtl/detail/inc/FunctorId.h | 2 +- .../rtl/detail/inc/forward_decls.h | 15 ++++- ReflectionTemplateLib/rtl/dispatch/functor.h | 29 ++++---- .../rtl/dispatch/lambda_hop.h | 67 +++++++++++-------- .../rtl/dispatch/lambda_hop_function.h | 40 ++++++----- .../rtl/dispatch/lambda_hop_method.h | 39 +++++------ ReflectionTemplateLib/rtl/inc/Function.h | 4 +- ReflectionTemplateLib/rtl/inc/Function.hpp | 4 +- ReflectionTemplateLib/rtl/inc/Method.h | 2 +- ReflectionTemplateLib/rtl/inc/Method.hpp | 6 +- ReflectionTemplateLib/rtl/rtl.h | 4 +- ReflectionTemplateLib/rtl/rtl_constants.h | 17 +++++ ReflectionTemplateLib/rtl/src/CxxMirror.cpp | 2 +- .../rtl/src/CxxMirrorToJson.cpp | 2 +- 24 files changed, 204 insertions(+), 171 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index dd2457ef..29fb08e1 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -20,31 +20,31 @@ namespace { static const rtl::lambda_function& getMessage_lambda = []() { - // No validation is performed internally and lambda_hop + // No validation is performed internally and lambda // will not return nullptr on signature mismatch. (by design) - return *(cxx::mirror().getFunction("getMessage")->lambda_hop()); + return *(cxx::mirror().getFunction("getMessage")->get_lambda()); }(); static const rtl::lambda_function& sendMessage_lambda = []() { - // No validation is performed internally and lambda_hop + // No validation is performed internally and lambda // will not return nullptr on signature mismatch. (by design) - return *(cxx::mirror().getFunction("sendMessage")->lambda_hop()); + return *(cxx::mirror().getFunction("sendMessage")->get_lambda()); }(); static const rtl::lambda_method& getMessageOnNode_lambda = []() { - // No validation is performed internally and lambda_hop + // No validation is performed internally and lambda // will not return nullptr on signature mismatch. (by design) - return *(cxx::mirror().getRecord("Node")->getMethod("getMessage")->lambda_hop()); + return *(cxx::mirror().getRecord("Node")->getMethod("getMessage")->get_lambda()); }(); static const rtl::lambda_method& sendMessageOnNode_lambda = []() { rtl::Record Node = cxx::mirror().getRecord("Node").value(); - // No validation is performed internally and lambda_hop + // No validation is performed internally and lambda // will not return nullptr on signature mismatch. (by design) - return *(cxx::mirror().getRecord("Node")->getMethod("sendMessage")->lambda_hop()); + return *(cxx::mirror().getRecord("Node")->getMethod("sendMessage")->get_lambda()); }(); } @@ -154,7 +154,7 @@ void ReflectedCallKnownReturn::set(benchmark::State& state) { if (passed) { - sendMessage_lambda.dispatch(bm::g_longStr); + sendMessage_lambda.hop(bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } @@ -168,7 +168,7 @@ void ReflectedCallKnownReturn::get(benchmark::State& state) { if (passed) { - auto retStr = getMessage_lambda.dispatch(bm::g_longStr); + auto retStr = getMessage_lambda.hop(bm::g_longStr); benchmark::DoNotOptimize(retStr); } } @@ -194,7 +194,7 @@ void ReflectedMethodCallKnownReturn::set(benchmark::State& state) { if (functor) { - sendMessageOnNode_lambda.dispatch(nodeObj, bm::g_longStr); + sendMessageOnNode_lambda.hop(nodeObj, bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } @@ -220,7 +220,7 @@ void ReflectedMethodCallKnownReturn::get(benchmark::State& state) { if (functor) { - auto retStr = getMessageOnNode_lambda.dispatch(nodeObj, bm::g_longStr); + auto retStr = getMessageOnNode_lambda.hop(nodeObj, bm::g_longStr); benchmark::DoNotOptimize(retStr); } } diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index d459fd79..bd07a5c3 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -24,9 +24,11 @@ BENCHMARK(ReflectedMethodCallUnknownReturn::set); BENCHMARK(NativeCall::get); BENCHMARK(FunctionPointerCall::get); +//BENCHMARK(ReflectedMethodCallKnownReturn::get); BENCHMARK(StdFunctionCall::get); BENCHMARK(ReflectedCallKnownReturn::get); BENCHMARK(ReflectedCallUnknownReturn::get); +//BENCHMARK(ReflectedMethodCallKnownReturn::get); BENCHMARK(StdFunctionMethodCall::get); BENCHMARK(ReflectedMethodCallKnownReturn::get); diff --git a/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp b/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp index 41492567..d6f62f6e 100644 --- a/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp +++ b/RTLTestRunApp/src/CxxMirrorTests/CxxMirrorObjectTest.cpp @@ -287,8 +287,8 @@ namespace rtl_tests // Even though the functions are registered in different namespaces, // the underlying FunctorIds (which identify function-pointers) must be equal. - const std::vector& cfunctorIds = cstrLen->getOverloads(); - const std::vector& stdfunctorIds = stdStrLen->getOverloads(); + const std::vector& cfunctorIds = cstrLen->getFunctors(); + const std::vector& stdfunctorIds = stdStrLen->getFunctors(); EXPECT_EQ(cfunctorIds, stdfunctorIds); } @@ -349,8 +349,8 @@ namespace rtl_tests // Despite different symbolic names, both reflect the same function-pointer. // Hence, their FunctorIds must be identical. - const std::vector& cfunctorIds = cstrLen->getOverloads(); - const std::vector& stdfunctorIds = stdStrLen->getOverloads(); + const std::vector& cfunctorIds = cstrLen->getFunctors(); + const std::vector& stdfunctorIds = stdStrLen->getFunctors(); EXPECT_EQ(cfunctorIds, stdfunctorIds); } diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index a5cc37eb..dd94db02 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -30,8 +30,8 @@ namespace rtl { return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); - assert(isAllGood && "new type-id-system not working."); + bool isFunctorGood = (pFunctor == pFunctorId.m_lambda->to_function<_signature...>()->template get_functor().f_ptr()); + assert(isFunctorGood && "new type-id-system not working."); pFunctor(std::forward<_signature>(params)...); return { error::None, RObject{} }; @@ -48,8 +48,8 @@ namespace rtl this is stored in _derivedType's (FunctorContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, _signature&&...params)-> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); - assert(isAllGood && "new type-id-system not working."); + bool isFunctorGood = (pFunctor == pFunctorId.m_lambda->to_function<_signature...>()->template get_functor<_returnType>().f_ptr()); + assert(isFunctorGood && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); @@ -89,14 +89,14 @@ namespace rtl template inline const detail::FunctorId SetupFunction<_derivedType>::addFunctor(_returnType(*pFunctor)(_signature...), std::size_t pRecordId) { - const dispatch::lambda_hop* lambdaPtr = nullptr; + const dispatch::lambda* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = cache::lambda_hop_function<_signature...>::instance(); + auto& lambdaCache = cache::lambda_function<_signature...>::instance(); auto& functorCache = cache::function_ptr<_returnType, _signature...>::instance(); - auto* functor = functorCache.push(pFunctor, pIndex); + auto& functor = functorCache.push(pFunctor, pIndex); auto& lambda = lambdaCache.push(functor); lambdaPtr = λ @@ -107,7 +107,7 @@ namespace rtl auto& functorCache = cache::function_ptr<_returnType, _signature...>::instance(); auto [functor, lambdaIndex] = functorCache.find(pFunctor); if (lambdaIndex != rtl::index_none) { - lambdaPtr = functor->getLambdaHop(); + lambdaPtr = functor->get_lambda(); } return lambdaIndex; }; diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 2d416b8b..dde8b903 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -34,8 +34,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); - assert(isAllGood && "new type-id-system not working."); + bool isFunctorGood = (pFunctor == pFunctorId.m_lambda->to_method<_recordType, _signature...>()->template get_functor().f_ptr()); + assert(isFunctorGood && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -57,8 +57,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); - assert(isAllGood && "new type-id-system not working."); + bool isFunctorGood = (pFunctor == pFunctorId.m_lambda->to_method<_recordType, _signature...>()->template get_functor<_returnType>().f_ptr()); + assert(isFunctorGood && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -101,8 +101,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); - assert(isAllGood && "new type-id-system not working."); + bool isLambdaGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->get_functor().get_lambda()); + assert(isLambdaGood && "new type-id-system not working."); const _recordType& target = pTargetObj.view<_recordType>()->get(); (target.*pFunctor)(std::forward<_signature>(params)...); @@ -120,8 +120,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isAllGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->m_functor->getLambdaHop()); - assert(isAllGood && "new type-id-system not working."); + bool isLambdaGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->get_functor().get_lambda()); + assert(isLambdaGood && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); //'target' is const and 'pFunctor' is const-member-function. @@ -163,13 +163,13 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...)) { - const dispatch::lambda_hop* lambdaPtr = nullptr; + const dispatch::lambda* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = cache::lambda_hop_method<_recordType, _signature...>::instance(); + auto& lambdaCache = cache::lambda_method<_recordType, _signature...>::instance(); auto& functorCache = cache::method_ptr<_recordType, _returnType, _signature...>::instance(); - auto* functor = functorCache.push(pFunctor, pIndex); + auto& functor = functorCache.push(pFunctor, pIndex); auto& lambda = lambdaCache.push(functor); lambdaPtr = λ @@ -181,7 +181,7 @@ namespace rtl::detail auto [functor, lambdaIndex] = functorCache.find(pFunctor); if (lambdaIndex != rtl::index_none) { - lambdaPtr = functor->getLambdaHop(); + lambdaPtr = functor->get_lambda(); } return lambdaIndex; }; @@ -234,13 +234,13 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const) { - const dispatch::lambda_hop* lambdaPtr = nullptr; + const dispatch::lambda* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = cache::lambda_hop_method<_recordType, _signature...>::instance(); + auto& lambdaCache = cache::lambda_method<_recordType, _signature...>::instance(); auto& functorCache = cache::const_method_ptr<_recordType, _returnType, _signature...>::instance(); - auto* functor = functorCache.push(pFunctor, pIndex); + auto& functor = functorCache.push(pFunctor, pIndex); auto& lambda = lambdaCache.push(functor); lambdaPtr = λ @@ -252,7 +252,7 @@ namespace rtl::detail auto [functor, lambdaIndex] = functorCache.find(pFunctor); if (lambdaIndex != rtl::index_none) { - lambdaPtr = functor->getLambdaHop(); + lambdaPtr = functor->get_lambda(); } return lambdaIndex; }; diff --git a/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h index 94ce76a0..e4a8826b 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h @@ -28,10 +28,10 @@ namespace rtl::cache return instance_; } - const dispatch::functor* push(return_t(record_t::* fptr)(signature_ts...) const, std::size_t lambda_index) const + const dispatch::functor& push(return_t(record_t::* fptr)(signature_ts...) const, std::size_t lambda_index) const { m_cache.emplace_back(std::make_pair(fptr, lambda_index)); - return &(m_cache.back().first); + return m_cache.back().first; } std::pair find(return_t(record_t::* fptr)(signature_ts...) const) const diff --git a/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h index 2337eee7..8167b8fe 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h @@ -28,10 +28,10 @@ namespace rtl::cache return instance_; } - const dispatch::functor* push(return_t(*fptr)(signature_ts...), std::size_t lambda_index) const + const dispatch::functor& push(return_t(*fptr)(signature_ts...), std::size_t lambda_index) const { m_cache.emplace_back(std::make_pair(fptr, lambda_index)); - return &(m_cache.back().first); + return m_cache.back().first; } std::pair find(return_t(*fptr)(signature_ts...)) const diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h index b27274e5..c64687c0 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h @@ -18,31 +18,31 @@ namespace rtl::cache { template - struct lambda_hop_function + struct lambda_function { - static const lambda_hop_function& instance() + static const lambda_function& instance() { - static const lambda_hop_function instance_; + static const lambda_function instance_; return instance_; } - const dispatch::lambda_hop_function& push(const dispatch::functor* fptr) const + const dispatch::lambda_function& push(const dispatch::functor& fptr) const { - m_cache.push_back(dispatch::lambda_hop_function(fptr)); - fptr->set_lambda(&m_cache.back()); + m_cache.push_back(dispatch::lambda_function(fptr)); + fptr.m_lambda = &m_cache.back(); return m_cache.back(); } - lambda_hop_function(lambda_hop_function&&) = delete; - lambda_hop_function(const lambda_hop_function&) = delete; - lambda_hop_function& operator=(lambda_hop_function&&) = delete; - lambda_hop_function& operator=(const lambda_hop_function&) = delete; + lambda_function(lambda_function&&) = delete; + lambda_function(const lambda_function&) = delete; + lambda_function& operator=(lambda_function&&) = delete; + lambda_function& operator=(const lambda_function&) = delete; private: // No reallocation occurs; original objects stay intact - mutable std::list> m_cache; + mutable std::list> m_cache; - lambda_hop_function() = default; + lambda_function() = default; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h index f72bc546..9d6c30c0 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h @@ -18,31 +18,31 @@ namespace rtl::cache { template - struct lambda_hop_method + struct lambda_method { - static const lambda_hop_method& instance() + static const lambda_method& instance() { - static const lambda_hop_method instance_; + static const lambda_method instance_; return instance_; } - const dispatch::lambda_hop_method& push(const dispatch::functor* fptr) const + const dispatch::lambda_method& push(const dispatch::functor& fptr) const { - m_cache.push_back(dispatch::lambda_hop_method(fptr)); - fptr->set_lambda(&m_cache.back()); + m_cache.push_back(dispatch::lambda_method(fptr)); + fptr.m_lambda = &m_cache.back(); return m_cache.back(); } - lambda_hop_method(lambda_hop_method&&) = delete; - lambda_hop_method(const lambda_hop_method&) = delete; - lambda_hop_method& operator=(lambda_hop_method&&) = delete; - lambda_hop_method& operator=(const lambda_hop_method&) = delete; + lambda_method(lambda_method&&) = delete; + lambda_method(const lambda_method&) = delete; + lambda_method& operator=(lambda_method&&) = delete; + lambda_method& operator=(const lambda_method&) = delete; private: // No reallocation occurs; original objects stay intact - mutable std::list> m_cache; + mutable std::list> m_cache; - lambda_hop_method() = default; + lambda_method() = default; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h index 16c19862..a607f1e2 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h @@ -28,10 +28,10 @@ namespace rtl::cache return instance_; } - const dispatch::functor* push(return_t(record_t::* fptr)(signature_ts...), std::size_t lambda_index) const + const dispatch::functor& push(return_t(record_t::* fptr)(signature_ts...), std::size_t lambda_index) const { m_cache.emplace_back(std::make_pair(fptr, lambda_index)); - return &(m_cache.back().first); + return m_cache.back().first; } std::pair find(return_t(record_t::* fptr)(signature_ts...)) const diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index 7dd8a163..f9a28da7 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -43,7 +43,7 @@ namespace rtl::detail //signature of functor as string. platform dependent, may not be very much readable format. std::string m_signature; - const dispatch::lambda_hop* m_lambda = nullptr; + const dispatch::lambda* m_lambda = nullptr; GETTER(std::size_t, LambdaIndex, m_lambdaIndex) GETTER(std::size_t, ReturnId, m_returnId); diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index 0497b75d..63456bd0 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -33,17 +33,26 @@ namespace rtl class FunctorContainer; } + namespace cache + { + template + struct lambda_function; + + template + struct lambda_method; + } + namespace dispatch { struct functor; - class lambda_hop; + struct lambda; template - struct lambda_hop_function; + class lambda_function; template - struct lambda_hop_method; + class lambda_method; template struct function_ptr; diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index 5f8e6152..06a6a9ce 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -19,23 +19,24 @@ namespace rtl::dispatch { struct functor { - constexpr void set_lambda(const lambda_hop* lambda) const - { - m_lambda = lambda; - } + std::size_t m_recordId = detail::TypeId<>::None; + std::size_t m_returnId = detail::TypeId<>::None; + std::size_t m_signatureId = detail::TypeId<>::None; - GETTER(std::size_t, ReturnId, m_returnId); - GETTER(std::size_t, RecordId, m_recordId); - GETTER(std::size_t, SignatureId, m_signatureId); - GETTER(lambda_hop*, LambdaHop, m_lambda); + std::vector m_argumentsId = {}; - protected: + detail::methodQ m_qualifier = detail::methodQ::None; - mutable const lambda_hop* m_lambda = nullptr; + GETTER_CPTR(lambda, _lambda, m_lambda) - std::size_t m_recordId = detail::TypeId<>::None; - std::size_t m_returnId = detail::TypeId<>::None; - std::size_t m_signatureId = detail::TypeId<>::None; - detail::methodQ m_qualifier = detail::methodQ::None; + private: + + mutable const lambda* m_lambda = nullptr; + + template + friend struct cache::lambda_function; + + template + friend struct cache::lambda_method; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h index c537db26..a783689a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h @@ -20,56 +20,67 @@ namespace rtl::dispatch { - struct lambda_hop + struct lambda { - template - constexpr bool is_member() const - { - return (m_functor->getRecordId() == detail::TypeId>::get() || - m_functor->getRecordId() == detail::TypeId>::get()); - } + protected: - template - constexpr bool is_returning() const - { - return (m_functor->getReturnId() == detail::TypeId>::get()); - } + const functor& m_functor; - template - constexpr bool is_signature() const - { - return (m_signatureId == detail::TypeId...>>::get()); - } + lambda(const functor& p_functor) noexcept + :m_functor(p_functor) + { } + + template + using function_t = lambda_function; + + template + using method_t = lambda_method; + + public: + + GETTER_CREF(functor, _functor, m_functor); template - constexpr const lambda_hop_function* get_function() const + constexpr const function_t* to_function() const { const std::size_t typeId = detail::TypeId...>>::get(); - if (typeId == m_signatureId) + if (typeId == m_functor.m_signatureId) { - return static_cast*>(this); + return static_cast*>(this); } return nullptr; } template - const lambda_hop_method* get_method() const + const method_t* to_method() const { std::size_t recordId = detail::TypeId::get(); std::size_t typeId = detail::TypeId...>>::get(); - if (typeId == m_signatureId && recordId == m_functor->getRecordId()) + if (typeId == m_functor.m_signatureId && recordId == m_functor.m_recordId) { - return static_cast*>(this); + return static_cast*>(this); } return nullptr; } - GETTER(std::size_t, SignatureId, m_signatureId); -// protected: + template + constexpr bool is_returning() const + { + return (m_functor.m_returnId == detail::TypeId>::get()); + } + + template + constexpr bool is_signature() const + { + return (m_functor.m_signatureId == detail::TypeId...>>::get()); + } - const functor* m_functor = nullptr; - std::size_t m_signatureId = detail::TypeId<>::None; - std::vector m_argumentsId = {}; + template + constexpr bool is_member() const + { + return (m_functor.m_recordId == detail::TypeId>::get() || + m_functor.m_recordId == detail::TypeId>::get()); + } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h index 4401acd7..17e2b4b4 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h @@ -17,39 +17,37 @@ namespace rtl::dispatch { template - struct lambda_hop_function: public lambda_hop + class lambda_function: public lambda { - lambda_hop_function(const functor* fptr) noexcept - { - m_functor = fptr; - m_signatureId = detail::TypeId...>>::get(); - detail::TypeId::get(m_argumentsId); - } + template + using fptr_t = typename function_ptr::functor_t; + + template + static constexpr bool is_argst_ok = std::is_same_v...>, std::tuple>; + + template + static constexpr bool noexcept_v = noexcept(std::declval>()(std::declval()...)); + + public: + + lambda_function(const functor& fptr) noexcept + :lambda(fptr) + { } template constexpr const function_ptr& get_functor() const { // Unchecked: using an incorrect argument or return type is undefined behaviour. // No validation is performed and the function will not return nullptr on mismatch. (By Design) - return *(static_cast*>(m_functor)); + return static_cast&>(m_functor); } template - constexpr decltype(auto) dispatch(args_t&&...params) const - noexcept(noexcept( - std::invoke(get_functor().f_ptr(),std::declval()...) - )) + constexpr decltype(auto) hop(args_t&&...params) const //noexcept(noexcept_v) { - constexpr bool signature_ok = std::is_same_v< - std::tuple...>, - std::tuple - >; - static_assert( signature_ok, "Argument types don't match signature."); - - using fptr_t = typename function_ptr::functor_t; - - fptr_t functor = get_functor().f_ptr(); + static_assert(is_argst_ok, "Argument types don't match signature."); + fptr_t functor = get_functor().f_ptr(); if constexpr (std::is_same_v) { (*functor)(std::forward(params)...); } diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h index a607488c..967659ff 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h @@ -13,46 +13,41 @@ #include "lambda_hop.h" #include "method_ptr.h" -#include namespace rtl::dispatch { template - struct lambda_hop_method : public lambda_hop + class lambda_method : public lambda { template using fptr_t = typename method_ptr::functor_t; - lambda_hop_method(const functor* functor) noexcept - { - m_functor = functor; - m_signatureId = detail::TypeId...>>::get(); - detail::TypeId::get(m_argumentsId); - } + template + static constexpr bool is_argst_ok = std::is_same_v...>, std::tuple>; + template + static constexpr bool noexcept_v = noexcept((std::declval().*std::declval>())(std::declval()...)); + + public: + + lambda_method(const functor& fptr) noexcept + :lambda(fptr) + { } + + // Unsafe: using an incorrect argument or return type is undefined behaviour. + // Not validated here and the function will not return nullptr on mismatch. (By Design) template constexpr const method_ptr& get_functor() const { - // Unchecked: using an incorrect argument or return type is undefined behaviour. - // No validation is performed and the function will not return nullptr on mismatch. (By Design) - return *(static_cast*>(m_functor)); + return static_cast&>(m_functor); } template - constexpr decltype(auto) dispatch(record_t& target, args_t&& ...params) const - noexcept(noexcept( - (std::declval().*std::declval>())(std::declval()...) - )) + constexpr decltype(auto) hop(record_t& target, args_t&& ...params) const noexcept(noexcept_v) { - constexpr bool signature_ok = std::is_same_v< - std::tuple...>, - std::tuple - >; - - static_assert( signature_ok, "Argument types don't match signature."); + static_assert(is_argst_ok, "Argument types don't match signature."); fptr_t functor = get_functor().f_ptr(); - if constexpr (std::is_same_v) { (target.*functor)(std::forward(params)...); } diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index a4a4e9b6..6310aaf4 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -81,7 +81,7 @@ namespace rtl { GETTER(std::string, Namespace, m_namespace); GETTER(std::string, FunctionName, m_function); GETTER(std::size_t, RecordTypeId, m_recordTypeId); - GETTER(std::vector, Overloads, m_functorIds); + GETTER(std::vector, Functors, m_functorIds); Function() = default; Function(Function&&) = default; @@ -96,7 +96,7 @@ namespace rtl { bool hasSignature() const; template - const dispatch::lambda_hop_function<_signature...>* lambda_hop(std::size_t pOverloadIndex = 0) const; + const dispatch::lambda_function<_signature...>* get_lambda(std::size_t pOverloadIndex = 0) const; template Return operator()(_args&&...params) const noexcept; diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index cf8f230b..56eea735 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -23,11 +23,11 @@ namespace rtl } template - const dispatch::lambda_hop_function<_signature...>* Function::lambda_hop(std::size_t pOverloadIndex) const + const dispatch::lambda_function<_signature...>* Function::get_lambda(std::size_t pOverloadIndex) const { if (pOverloadIndex < m_functorIds.size()) { - return m_functorIds[pOverloadIndex].m_lambda->get_function<_signature...>(); + return m_functorIds[pOverloadIndex].m_lambda->to_function<_signature...>(); } return nullptr; } diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index d6394d03..2733d58c 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -67,7 +67,7 @@ namespace rtl { const detail::NonConstInvoker<_signature...> bind(constCast&& pTarget) const; template - const dispatch::lambda_hop_method<_recordType, _signature...>* lambda_hop(std::size_t pOverloadIndex = 0) const; + const dispatch::lambda_method<_recordType, _signature...>* get_lambda(std::size_t pOverloadIndex = 0) const; /* @method: operator()() @return: lambda diff --git a/ReflectionTemplateLib/rtl/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp index 86517622..57bdbab5 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.hpp +++ b/ReflectionTemplateLib/rtl/inc/Method.hpp @@ -30,12 +30,12 @@ namespace rtl template - const dispatch::lambda_hop_method<_recordType, _signature...>* Method::lambda_hop(std::size_t pOverloadIndex) const + const dispatch::lambda_method<_recordType, _signature...>* Method::get_lambda(std::size_t pOverloadIndex) const { - auto& functorIds = getOverloads(); + auto& functorIds = getFunctors(); if (pOverloadIndex < functorIds.size()) { - return functorIds[pOverloadIndex].m_lambda->get_method<_recordType, _signature...>(); + return functorIds[pOverloadIndex].m_lambda->to_method<_recordType, _signature...>(); } return nullptr; } diff --git a/ReflectionTemplateLib/rtl/rtl.h b/ReflectionTemplateLib/rtl/rtl.h index 9a803b14..4c53df70 100644 --- a/ReflectionTemplateLib/rtl/rtl.h +++ b/ReflectionTemplateLib/rtl/rtl.h @@ -105,8 +105,8 @@ namespace rtl { template - using lambda_function = dispatch::lambda_hop_function; + using lambda_function = dispatch::lambda_function; template - using lambda_method = dispatch::lambda_hop_method; + using lambda_method = dispatch::lambda_method; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/rtl_constants.h b/ReflectionTemplateLib/rtl/rtl_constants.h index 09e927c4..99af7fb8 100644 --- a/ReflectionTemplateLib/rtl/rtl_constants.h +++ b/ReflectionTemplateLib/rtl/rtl_constants.h @@ -144,6 +144,12 @@ namespace rtl::detail return (std::string(pRecordName) + "::" + std::string(pRecordName) + "()"); } + +#define GETTER_(_varType, _name, _var) \ + inline constexpr const _varType& _name() const { \ + return _var; \ + } + #define GETTER(_varType, _name, _var) \ inline constexpr const _varType& get##_name() const { \ return _var; \ @@ -154,6 +160,17 @@ namespace rtl::detail return _var; \ } + +#define GETTER_CPTR_(_varType, _name, _var) \ + constexpr inline const _varType* _name() const { \ + return _var; \ + } + +#define GETTER_CPTR(_varType, _name, _var) \ + constexpr inline const _varType* get##_name() const { \ + return _var; \ + } + #define GETTER_CREF(_varType, _name, _var) \ inline const _varType& get##_name() const { \ return _var; \ diff --git a/ReflectionTemplateLib/rtl/src/CxxMirror.cpp b/ReflectionTemplateLib/rtl/src/CxxMirror.cpp index 72d8f202..9054699d 100644 --- a/ReflectionTemplateLib/rtl/src/CxxMirror.cpp +++ b/ReflectionTemplateLib/rtl/src/CxxMirror.cpp @@ -32,7 +32,7 @@ namespace rtl { const Record& record = itr->second; Method ctors = record.getMethod(detail::ctor_name(record.getRecordName())).value(); - const_cast(pTarget).m_objectId.m_clonerId = ctors.getOverloads()[detail::Index::CopyCtor]; + const_cast(pTarget).m_objectId.m_clonerId = ctors.getFunctors()[detail::Index::CopyCtor]; return error::None; } return error::CloningDisabled; diff --git a/ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp b/ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp index fe35b583..9905c356 100644 --- a/ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp +++ b/ReflectionTemplateLib/rtl/src/CxxMirrorToJson.cpp @@ -40,7 +40,7 @@ static const std::string toJson(const FunctorId& pFunctorId) static const std::string toJson(const Function& pFunction) { std::stringstream sout; - const auto& functors = pFunction.getOverloads(); + const auto& functors = pFunction.getFunctors(); const std::string& record = pFunction.getRecordName(); const std::string& nmspace = pFunction.getNamespace(); From 88f189d31185f43694febbaec98a5cf2b7ce050d Mon Sep 17 00:00:00 2001 From: neeraj Date: Mon, 22 Sep 2025 13:11:08 +0530 Subject: [PATCH 23/58] return value propogation optimized. --- RTLBenchmarkApp/src/BenchMark.cpp | 13 ++-- RTLBenchmarkApp/src/BenchMark.h | 4 +- .../src/ReflectedCallKnownReturn.cpp | 60 +++++++++++++++++-- .../src/ReflectedCallKnownReturn.h | 12 +++- .../src/ReflectedCallUnknownReturn.cpp | 8 +-- .../src/ReflectedCallUnknownReturn.h | 4 +- RTLBenchmarkApp/src/StandardCall.cpp | 12 ++-- RTLBenchmarkApp/src/StdFunction.cpp | 10 ++-- RTLBenchmarkApp/src/main.cpp | 19 +++--- .../rtl/builder/FunctorContainer.h | 2 +- .../rtl/builder/SetupFunction.hpp | 2 +- .../rtl/builder/SetupMethod.hpp | 4 +- .../rtl/cache/CMakeLists.txt | 4 +- ...hop_function.h => cache_lambda_function.h} | 2 +- ...bda_hop_method.h => cache_lambda_method.h} | 2 +- .../rtl/detail/inc/FunctorId.h | 2 +- .../rtl/dispatch/CMakeLists.txt | 6 +- .../rtl/dispatch/function_ptr.h | 4 +- .../rtl/dispatch/{lambda_hop.h => lambda.h} | 6 +- ...ambda_hop_function.h => lambda_function.h} | 23 ++++--- .../{lambda_hop_method.h => lambda_method.h} | 23 ++++--- .../rtl/dispatch/method_ptr.h | 2 +- ReflectionTemplateLib/rtl/inc/Function.h | 2 +- ReflectionTemplateLib/rtl/inc/Method.h | 2 +- ReflectionTemplateLib/rtl/inc/RObject.h | 4 +- ReflectionTemplateLib/rtl/rtl.h | 8 +-- ReflectionTemplateLib/rtl/rtl_constants.h | 13 ---- ReflectionTemplateLib/rtl/rtl_traits.h | 2 - ReflectionTemplateLib/rtl/rtl_typeid.h | 1 - ReflectionTemplateLib/rtl/src/CxxMirror.cpp | 1 - 30 files changed, 143 insertions(+), 114 deletions(-) rename ReflectionTemplateLib/rtl/cache/{cache_lambda_hop_function.h => cache_lambda_function.h} (98%) rename ReflectionTemplateLib/rtl/cache/{cache_lambda_hop_method.h => cache_lambda_method.h} (98%) rename ReflectionTemplateLib/rtl/dispatch/{lambda_hop.h => lambda.h} (95%) rename ReflectionTemplateLib/rtl/dispatch/{lambda_hop_function.h => lambda_function.h} (69%) rename ReflectionTemplateLib/rtl/dispatch/{lambda_hop_method.h => lambda_method.h} (68%) diff --git a/RTLBenchmarkApp/src/BenchMark.cpp b/RTLBenchmarkApp/src/BenchMark.cpp index 350617aa..2b1ef9f1 100644 --- a/RTLBenchmarkApp/src/BenchMark.cpp +++ b/RTLBenchmarkApp/src/BenchMark.cpp @@ -1,11 +1,10 @@ #include -#include -#include +#include #include "BenchMark.h" -#include + namespace bm @@ -20,21 +19,21 @@ namespace bm namespace bm { - void sendMessage(argStr_t pMsg) + void sendMessage(argStr_t pMsg) noexcept { if(g_work_load){ g_work_done = perform_work(pMsg); } } - void Node::sendMessage(argStr_t pMsg) + void Node::sendMessage(argStr_t pMsg) noexcept { if(g_work_load){ g_work_done = perform_work(pMsg); } } - retStr_t getMessage(argStr_t pMsg) + retStr_t getMessage(argStr_t pMsg) noexcept { if(g_work_load){ g_work_done = perform_work(pMsg); @@ -42,7 +41,7 @@ namespace bm return retStr_t(g_work_done->c_str()); } - retStr_t Node::getMessage(argStr_t pMsg) + retStr_t Node::getMessage(argStr_t pMsg) noexcept { if(g_work_load){ g_work_done = perform_work(pMsg); diff --git a/RTLBenchmarkApp/src/BenchMark.h b/RTLBenchmarkApp/src/BenchMark.h index ac27f784..a6bbc513 100644 --- a/RTLBenchmarkApp/src/BenchMark.h +++ b/RTLBenchmarkApp/src/BenchMark.h @@ -10,8 +10,8 @@ namespace bm struct Node { - void sendMessage(argStr_t); - retStr_t getMessage(argStr_t); + void sendMessage(argStr_t) noexcept; + retStr_t getMessage(argStr_t) noexcept; }; } diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 29fb08e1..1f074814 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -122,6 +122,58 @@ void FunctionPointerCall::set(benchmark::State& state) } +void MethodFnPointerCall::set(benchmark::State& state) +{ + static bm::Node nodeObj; + static auto functor = []() -> void(bm::Node::*)(bm::argStr_t) + { + // Must be checked: Passing an incorrect argument or return type is undefined behaviour. + if (sendMessageOnNode_lambda.is_returning() && sendMessageOnNode_lambda.is_signature()) + { + // No validation is performed internally and the function will not return nullptr on mismatch. + return sendMessageOnNode_lambda.get_functor().f_ptr(); + } + std::cout << "[8] error: signature mismatch.\n"; + return nullptr; + }(); + + for (auto _ : state) + { + if (functor) + { + (nodeObj.*functor)(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); + } + } +} + + +void MethodFnPointerCall::get(benchmark::State& state) +{ + static bm::Node nodeObj; + static auto functor = []() -> bm::retStr_t(bm::Node::*)(bm::argStr_t) + { + // Must be checked: Passing an incorrect argument or return type is undefined behaviour. + if (getMessageOnNode_lambda.is_returning() && getMessageOnNode_lambda.is_signature()) + { + // No validation is performed internally and the function will not return nullptr on mismatch. + return getMessageOnNode_lambda.get_functor().f_ptr(); + } + std::cout << "[9] error: signature mismatch.\n"; + return nullptr; + }(); + + for (auto _ : state) + { + if (functor) + { + auto ret = (nodeObj.*functor)(bm::g_longStr); + benchmark::DoNotOptimize(ret); + } + } +} + + void FunctionPointerCall::get(benchmark::State& state) { static auto* functor = []() -> bm::retStr_t(*)(bm::argStr_t) @@ -147,7 +199,7 @@ void FunctionPointerCall::get(benchmark::State& state) } -void ReflectedCallKnownReturn::set(benchmark::State& state) +void RtlReflectedCall::set(benchmark::State& state) { static auto passed = _test0(); for (auto _ : state) @@ -161,7 +213,7 @@ void ReflectedCallKnownReturn::set(benchmark::State& state) } -void ReflectedCallKnownReturn::get(benchmark::State& state) +void RtlReflectedCall::get(benchmark::State& state) { static auto passed = _test2(); for (auto _: state) @@ -175,7 +227,7 @@ void ReflectedCallKnownReturn::get(benchmark::State& state) } -void ReflectedMethodCallKnownReturn::set(benchmark::State& state) +void RtlReflectedMethodCall::set(benchmark::State& state) { static bm::Node nodeObj; static auto functor = []() -> void(bm::Node::*)(bm::argStr_t) @@ -201,7 +253,7 @@ void ReflectedMethodCallKnownReturn::set(benchmark::State& state) } -void ReflectedMethodCallKnownReturn::get(benchmark::State& state) +void RtlReflectedMethodCall::get(benchmark::State& state) { static bm::Node nodeObj; static auto functor = []() -> bm::retStr_t(bm::Node::*)(bm::argStr_t) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h index eefbd04c..e1f9c47a 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h @@ -2,7 +2,7 @@ #include -struct ReflectedCallKnownReturn +struct RtlReflectedCall { static void set(benchmark::State& state); @@ -18,7 +18,15 @@ struct FunctionPointerCall }; -struct ReflectedMethodCallKnownReturn +struct MethodFnPointerCall +{ + static void set(benchmark::State& state); + + static void get(benchmark::State& state); +}; + + +struct RtlReflectedMethodCall { static void set(benchmark::State& state); diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index 91ca4fb4..db9b2ee9 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -84,7 +84,7 @@ namespace -void ReflectedCallUnknownReturn::set(benchmark::State& state) +void RtlReflectedCall_retUnknown::set(benchmark::State& state) { static auto _ = _test0(); for (auto _ : state) @@ -95,7 +95,7 @@ void ReflectedCallUnknownReturn::set(benchmark::State& state) } -void ReflectedCallUnknownReturn::get(benchmark::State& state) +void RtlReflectedCall_retUnknown::get(benchmark::State& state) { static auto _ = _test2(); for (auto _ : state) @@ -106,7 +106,7 @@ void ReflectedCallUnknownReturn::get(benchmark::State& state) } -void ReflectedMethodCallUnknownReturn::set(benchmark::State& state) +void RtlReflectionMethodCall_retUnknown::set(benchmark::State& state) { static auto _ = _test1(); for (auto _ : state) @@ -117,7 +117,7 @@ void ReflectedMethodCallUnknownReturn::set(benchmark::State& state) } -void ReflectedMethodCallUnknownReturn::get(benchmark::State& state) +void RtlReflectionMethodCall_retUnknown::get(benchmark::State& state) { static auto _ = _test3(); for (auto _ : state) diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h index 65c28df9..c2890430 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h @@ -2,7 +2,7 @@ #include -struct ReflectedCallUnknownReturn +struct RtlReflectedCall_retUnknown { static void set(benchmark::State& state); @@ -10,7 +10,7 @@ struct ReflectedCallUnknownReturn }; -struct ReflectedMethodCallUnknownReturn +struct RtlReflectionMethodCall_retUnknown { static void set(benchmark::State& state); diff --git a/RTLBenchmarkApp/src/StandardCall.cpp b/RTLBenchmarkApp/src/StandardCall.cpp index 419fd315..53294634 100644 --- a/RTLBenchmarkApp/src/StandardCall.cpp +++ b/RTLBenchmarkApp/src/StandardCall.cpp @@ -10,7 +10,7 @@ namespace { static auto _put_line = []() { std::cout << "----------------------------------------" - "----------------------------------------" << std::endl; + "------------------------------------------" << std::endl; return 0; }; @@ -31,11 +31,11 @@ namespace bm extern std::function SendMessage; - extern std::function NodeSendMessage; + extern std::function NodeSendMessage; extern std::function GetMessage; - extern std::function NodeGetMessage; + extern std::function NodeGetMessage; } @@ -72,10 +72,11 @@ void StdFunctionCall::set(benchmark::State& state) void StdFunctionMethodCall::set(benchmark::State& state) { + static bm::Node nodeObj; static auto _=_new_line(); for (auto _: state) { - bm::NodeSendMessage(bm::g_longStr); + bm::NodeSendMessage(nodeObj, bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } @@ -93,9 +94,10 @@ void StdFunctionCall::get(benchmark::State& state) void StdFunctionMethodCall::get(benchmark::State& state) { + static bm::Node nodeObj; static auto _=_new_line(); for (auto _: state) { - benchmark::DoNotOptimize(bm::NodeGetMessage(bm::g_longStr)); + benchmark::DoNotOptimize(bm::NodeGetMessage(nodeObj, bm::g_longStr)); } } \ No newline at end of file diff --git a/RTLBenchmarkApp/src/StdFunction.cpp b/RTLBenchmarkApp/src/StdFunction.cpp index b7c170e3..f3998942 100644 --- a/RTLBenchmarkApp/src/StdFunction.cpp +++ b/RTLBenchmarkApp/src/StdFunction.cpp @@ -19,8 +19,6 @@ namespace bm namespace bm { - static Node node; - extern void sendMessage(argStr_t); extern retStr_t getMessage(argStr_t); @@ -30,9 +28,9 @@ namespace bm bm::sendMessage(pMsg); }; - std::function NodeSendMessage = [](bm::argStr_t& pMsg) + std::function NodeSendMessage = [](bm::Node pNode, bm::argStr_t& pMsg) { - node.sendMessage(pMsg); + pNode.sendMessage(pMsg); }; std::function GetMessage = [](bm::argStr_t& pMsg) @@ -41,9 +39,9 @@ namespace bm return retMsg; }; - std::function NodeGetMessage = [](bm::argStr_t& pMsg) + std::function NodeGetMessage = [](bm::Node pNode, bm::argStr_t& pMsg) { - auto retMsg = node.getMessage(pMsg); + auto retMsg = pNode.getMessage(pMsg); return retMsg; }; } diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index bd07a5c3..b9a7d869 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -1,6 +1,5 @@ #include -#include #include #include "StandardCall.h" @@ -9,30 +8,32 @@ BENCHMARK(NativeCall::set); BENCHMARK(FunctionPointerCall::set); +BENCHMARK(MethodFnPointerCall::set); //BENCHMARK(ReflectedCallKnownReturn::set); //BENCHMARK(ReflectedCallKnownReturn::set); BENCHMARK(StdFunctionCall::set); -BENCHMARK(ReflectedCallKnownReturn::set); -BENCHMARK(ReflectedCallUnknownReturn::set); +BENCHMARK(RtlReflectedCall::set); +BENCHMARK(RtlReflectedCall_retUnknown::set); BENCHMARK(StdFunctionMethodCall::set); -BENCHMARK(ReflectedMethodCallKnownReturn::set); -BENCHMARK(ReflectedMethodCallUnknownReturn::set); +BENCHMARK(RtlReflectedMethodCall::set); +BENCHMARK(RtlReflectionMethodCall_retUnknown::set); BENCHMARK(NativeCall::get); BENCHMARK(FunctionPointerCall::get); +BENCHMARK(MethodFnPointerCall::get); //BENCHMARK(ReflectedMethodCallKnownReturn::get); BENCHMARK(StdFunctionCall::get); -BENCHMARK(ReflectedCallKnownReturn::get); -BENCHMARK(ReflectedCallUnknownReturn::get); +BENCHMARK(RtlReflectedCall::get); +BENCHMARK(RtlReflectedCall_retUnknown::get); //BENCHMARK(ReflectedMethodCallKnownReturn::get); BENCHMARK(StdFunctionMethodCall::get); -BENCHMARK(ReflectedMethodCallKnownReturn::get); -BENCHMARK(ReflectedMethodCallUnknownReturn::get); +BENCHMARK(RtlReflectedMethodCall::get); +BENCHMARK(RtlReflectionMethodCall_retUnknown::get); namespace bm { diff --git a/ReflectionTemplateLib/rtl/builder/FunctorContainer.h b/ReflectionTemplateLib/rtl/builder/FunctorContainer.h index dba8bd9a..31c1e82f 100644 --- a/ReflectionTemplateLib/rtl/builder/FunctorContainer.h +++ b/ReflectionTemplateLib/rtl/builder/FunctorContainer.h @@ -30,7 +30,7 @@ namespace rtl { /* @class: FunctorContainer @param: '_signature...' (combination of any types) - * container class for holding lambda_hop's wrapping functor, constructor calls of same signatures. + * container class for holding std::function, wrapping functor, constructor calls of same signatures. * maintains a std::vector with static lifetime. */ template class FunctorContainer : public SetupFunction>, diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index dd94db02..080ea460 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -13,7 +13,7 @@ #include -#include "cache_lambda_hop_function.h" +#include "cache_lambda_function.h" #include "cache_function_ptr.h" #include "SetupFunction.h" diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index dde8b903..1bf64725 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -18,10 +18,10 @@ #include "SetupMethod.h" #include "RObjectBuilder.hpp" -#include "lambda_hop_method.h" +#include "lambda_method.h" #include "cache_method_ptr.h" #include "cache_const_method_ptr.h" -#include "cache_lambda_hop_method.h" +#include "cache_lambda_method.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/cache/CMakeLists.txt b/ReflectionTemplateLib/rtl/cache/CMakeLists.txt index 24ac7968..4e5af74d 100644 --- a/ReflectionTemplateLib/rtl/cache/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/cache/CMakeLists.txt @@ -2,8 +2,8 @@ # Collect headers (absolute paths) set(LOCAL_HEADERS - "${CMAKE_CURRENT_SOURCE_DIR}/cache_lambda_hop_method.h" - "${CMAKE_CURRENT_SOURCE_DIR}/cache_lambda_hop_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/cache_lambda_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/cache_lambda_function.h" "${CMAKE_CURRENT_SOURCE_DIR}/cache_function_ptr.h" "${CMAKE_CURRENT_SOURCE_DIR}/cache_method_ptr.h" "${CMAKE_CURRENT_SOURCE_DIR}/cache_const_method_ptr.h" diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h similarity index 98% rename from ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h rename to ReflectionTemplateLib/rtl/cache/cache_lambda_function.h index c64687c0..0bc1ed17 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_function.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h @@ -13,7 +13,7 @@ #include -#include "lambda_hop_function.h" +#include "lambda_function.h" namespace rtl::cache { diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h similarity index 98% rename from ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h rename to ReflectionTemplateLib/rtl/cache/cache_lambda_method.h index 9d6c30c0..f096814d 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_hop_method.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h @@ -13,7 +13,7 @@ #include -#include "lambda_hop_method.h" +#include "lambda_method.h" namespace rtl::cache { diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index f9a28da7..23fcd69f 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -14,7 +14,7 @@ #include "rtl_typeid.h" #include "rtl_constants.h" #include "forward_decls.h" -#include "lambda_hop_method.h" +#include "lambda_method.h" namespace rtl::detail diff --git a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt index 6be5bbee..d1c8956b 100644 --- a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt @@ -8,9 +8,9 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/method_ptr.h" "${CMAKE_CURRENT_SOURCE_DIR}/const_method_ptr.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_method.h" - "${CMAKE_CURRENT_SOURCE_DIR}/lambda_hop_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function.h" ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/dispatch/function_ptr.h b/ReflectionTemplateLib/rtl/dispatch/function_ptr.h index fcf92c5d..7de9df89 100644 --- a/ReflectionTemplateLib/rtl/dispatch/function_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/function_ptr.h @@ -11,8 +11,6 @@ #pragma once -#include - #include "functor.h" namespace rtl::dispatch @@ -22,7 +20,7 @@ namespace rtl::dispatch { using functor_t = return_t(*)(signature_ts...); - constexpr functor_t f_ptr() const + [[nodiscard]] constexpr auto f_ptr() const { return m_functor; } diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h similarity index 95% rename from ReflectionTemplateLib/rtl/dispatch/lambda_hop.h rename to ReflectionTemplateLib/rtl/dispatch/lambda.h index a783689a..b2cfde79 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -11,11 +11,7 @@ #pragma once -#include - #include "rtl_traits.h" -#include "rtl_typeid.h" -#include "rtl_constants.h" #include "functor.h" namespace rtl::dispatch @@ -52,7 +48,7 @@ namespace rtl::dispatch } template - const method_t* to_method() const + constexpr const method_t* to_method() const { std::size_t recordId = detail::TypeId::get(); std::size_t typeId = detail::TypeId...>>::get(); diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h similarity index 69% rename from ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h rename to ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 17e2b4b4..690d6c15 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -11,7 +11,7 @@ #pragma once -#include "lambda_hop.h" +#include "lambda.h" #include "function_ptr.h" namespace rtl::dispatch @@ -23,7 +23,7 @@ namespace rtl::dispatch using fptr_t = typename function_ptr::functor_t; template - static constexpr bool is_argst_ok = std::is_same_v...>, std::tuple>; + static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; template static constexpr bool noexcept_v = noexcept(std::declval>()(std::declval()...)); @@ -35,7 +35,7 @@ namespace rtl::dispatch { } template - constexpr const function_ptr& get_functor() const + [[nodiscard]] constexpr auto& get_functor() const { // Unchecked: using an incorrect argument or return type is undefined behaviour. // No validation is performed and the function will not return nullptr on mismatch. (By Design) @@ -43,17 +43,14 @@ namespace rtl::dispatch } template - constexpr decltype(auto) hop(args_t&&...params) const //noexcept(noexcept_v) + [[nodiscard]] constexpr decltype(auto) hop(args_t&&...params) const noexcept(noexcept_v) { - static_assert(is_argst_ok, "Argument types don't match signature."); - - fptr_t functor = get_functor().f_ptr(); - if constexpr (std::is_same_v) { - (*functor)(std::forward(params)...); - } - else { - return (*functor)(std::forward(params)...); - } + static_assert(is_args_t_ok, "Argument types don't match signature."); + + constexpr auto call = [](auto fp, auto&&... a) -> decltype(auto) { + return (*fp)(std::forward(a)...); + }; + return call(get_functor().f_ptr(), std::forward(params)...); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h similarity index 68% rename from ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h rename to ReflectionTemplateLib/rtl/dispatch/lambda_method.h index 967659ff..dfd1e9a8 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_hop_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -11,7 +11,7 @@ #pragma once -#include "lambda_hop.h" +#include "lambda.h" #include "method_ptr.h" namespace rtl::dispatch @@ -23,7 +23,7 @@ namespace rtl::dispatch using fptr_t = typename method_ptr::functor_t; template - static constexpr bool is_argst_ok = std::is_same_v...>, std::tuple>; + static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; template static constexpr bool noexcept_v = noexcept((std::declval().*std::declval>())(std::declval()...)); @@ -37,23 +37,20 @@ namespace rtl::dispatch // Unsafe: using an incorrect argument or return type is undefined behaviour. // Not validated here and the function will not return nullptr on mismatch. (By Design) template - constexpr const method_ptr& get_functor() const + [[nodiscard]] constexpr auto& get_functor() const { return static_cast&>(m_functor); } template - constexpr decltype(auto) hop(record_t& target, args_t&& ...params) const noexcept(noexcept_v) + [[nodiscard]] constexpr decltype(auto) hop(record_t& target, args_t&& ...params) const noexcept(noexcept_v) { - static_assert(is_argst_ok, "Argument types don't match signature."); - - fptr_t functor = get_functor().f_ptr(); - if constexpr (std::is_same_v) { - (target.*functor)(std::forward(params)...); - } - else { - return (target.*functor)(std::forward(params)...); - } + static_assert(is_args_t_ok, "Argument types don't match signature."); + + constexpr auto call = [](record_t& obj, auto fp, auto&&... a) -> decltype(auto) { + return (obj.*fp)(std::forward(a)...); + }; + return call(target, get_functor().f_ptr(), std::forward(params)...); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h index 12563781..60ae79fb 100644 --- a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h @@ -22,7 +22,7 @@ namespace rtl::dispatch { using functor_t = return_t(record_t::*)(signature_ts...); - constexpr functor_t f_ptr() const + [[nodiscard]] constexpr auto f_ptr() const { return m_functor; } diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 6310aaf4..1df345be 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -18,7 +18,7 @@ #include "FunctorId.h" #include "rtl_constants.h" #include "FunctionCaller.h" -#include "lambda_hop_function.h" +#include "lambda_function.h" namespace rtl { diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index 2733d58c..a3b551b3 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -16,7 +16,7 @@ #include "RObject.h" #include "Function.h" #include "MethodInvoker.h" -#include "lambda_hop_method.h" +#include "lambda_method.h" namespace rtl { diff --git a/ReflectionTemplateLib/rtl/inc/RObject.h b/ReflectionTemplateLib/rtl/inc/RObject.h index e91f162c..3705c3a7 100644 --- a/ReflectionTemplateLib/rtl/inc/RObject.h +++ b/ReflectionTemplateLib/rtl/inc/RObject.h @@ -11,15 +11,13 @@ #pragma once -#include #include -#include #include "view.h" #include "RObjectId.h" -#include "rtl_typeid.h" #include "rtl_traits.h" +#include "rtl_errors.h" #include "forward_decls.h" namespace rtl::detail diff --git a/ReflectionTemplateLib/rtl/rtl.h b/ReflectionTemplateLib/rtl/rtl.h index 4c53df70..a21b849a 100644 --- a/ReflectionTemplateLib/rtl/rtl.h +++ b/ReflectionTemplateLib/rtl/rtl.h @@ -104,9 +104,9 @@ namespace rtl { - template - using lambda_function = dispatch::lambda_function; + template + using lambda_function = dispatch::lambda_function; - template - using lambda_method = dispatch::lambda_method; + template + using lambda_method = dispatch::lambda_method; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/rtl_constants.h b/ReflectionTemplateLib/rtl/rtl_constants.h index 99af7fb8..aeb28150 100644 --- a/ReflectionTemplateLib/rtl/rtl_constants.h +++ b/ReflectionTemplateLib/rtl/rtl_constants.h @@ -11,8 +11,6 @@ #pragma once -#include "rtl_errors.h" - namespace rtl { // Allocation policy for rtl::RObject. @@ -144,12 +142,6 @@ namespace rtl::detail return (std::string(pRecordName) + "::" + std::string(pRecordName) + "()"); } - -#define GETTER_(_varType, _name, _var) \ - inline constexpr const _varType& _name() const { \ - return _var; \ - } - #define GETTER(_varType, _name, _var) \ inline constexpr const _varType& get##_name() const { \ return _var; \ @@ -161,11 +153,6 @@ namespace rtl::detail } -#define GETTER_CPTR_(_varType, _name, _var) \ - constexpr inline const _varType* _name() const { \ - return _var; \ - } - #define GETTER_CPTR(_varType, _name, _var) \ constexpr inline const _varType* get##_name() const { \ return _var; \ diff --git a/ReflectionTemplateLib/rtl/rtl_traits.h b/ReflectionTemplateLib/rtl/rtl_traits.h index d2ccb404..84f4d631 100644 --- a/ReflectionTemplateLib/rtl/rtl_traits.h +++ b/ReflectionTemplateLib/rtl/rtl_traits.h @@ -12,8 +12,6 @@ #pragma once #include -#include -#include #include #include #include diff --git a/ReflectionTemplateLib/rtl/rtl_typeid.h b/ReflectionTemplateLib/rtl/rtl_typeid.h index 2e170f01..e898b588 100644 --- a/ReflectionTemplateLib/rtl/rtl_typeid.h +++ b/ReflectionTemplateLib/rtl/rtl_typeid.h @@ -14,7 +14,6 @@ #include #include #include -#include namespace rtl { diff --git a/ReflectionTemplateLib/rtl/src/CxxMirror.cpp b/ReflectionTemplateLib/rtl/src/CxxMirror.cpp index 9054699d..e75c71f4 100644 --- a/ReflectionTemplateLib/rtl/src/CxxMirror.cpp +++ b/ReflectionTemplateLib/rtl/src/CxxMirror.cpp @@ -11,7 +11,6 @@ #include "RObject.h" #include "CxxMirror.h" -#include "ReflectCast.h" namespace rtl { From e72d37a725b0943dfe8f156b4ad774e5c922e828 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Mon, 22 Sep 2025 14:03:25 +0530 Subject: [PATCH 24/58] removed temporary affecting stats, from benchmark. --- RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp | 12 ++++-------- ReflectionTemplateLib/rtl/dispatch/lambda_function.h | 6 +++--- ReflectionTemplateLib/rtl/dispatch/lambda_method.h | 4 ++-- 3 files changed, 9 insertions(+), 13 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 1f074814..9247b0a4 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -167,8 +167,7 @@ void MethodFnPointerCall::get(benchmark::State& state) { if (functor) { - auto ret = (nodeObj.*functor)(bm::g_longStr); - benchmark::DoNotOptimize(ret); + benchmark::DoNotOptimize((nodeObj.*functor)(bm::g_longStr)); } } } @@ -192,8 +191,7 @@ void FunctionPointerCall::get(benchmark::State& state) { if (functor) { - auto ret = (*functor)(bm::g_longStr); - benchmark::DoNotOptimize(ret); + benchmark::DoNotOptimize((*functor)(bm::g_longStr)); } } } @@ -220,8 +218,7 @@ void RtlReflectedCall::get(benchmark::State& state) { if (passed) { - auto retStr = getMessage_lambda.hop(bm::g_longStr); - benchmark::DoNotOptimize(retStr); + benchmark::DoNotOptimize(getMessage_lambda.hop(bm::g_longStr)); } } } @@ -272,8 +269,7 @@ void RtlReflectedMethodCall::get(benchmark::State& state) { if (functor) { - auto retStr = getMessageOnNode_lambda.hop(nodeObj, bm::g_longStr); - benchmark::DoNotOptimize(retStr); + benchmark::DoNotOptimize(getMessageOnNode_lambda.hop(nodeObj, bm::g_longStr)); } } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 690d6c15..86bc612a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -46,11 +46,11 @@ namespace rtl::dispatch [[nodiscard]] constexpr decltype(auto) hop(args_t&&...params) const noexcept(noexcept_v) { static_assert(is_args_t_ok, "Argument types don't match signature."); - - constexpr auto call = [](auto fp, auto&&... a) -> decltype(auto) { + + constexpr auto hopper = [](auto fp, auto&&... a) -> decltype(auto) { return (*fp)(std::forward(a)...); }; - return call(get_functor().f_ptr(), std::forward(params)...); + return hopper(get_functor().f_ptr(), std::forward(params)...); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index dfd1e9a8..1d7fd42c 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -47,10 +47,10 @@ namespace rtl::dispatch { static_assert(is_args_t_ok, "Argument types don't match signature."); - constexpr auto call = [](record_t& obj, auto fp, auto&&... a) -> decltype(auto) { + constexpr auto hopper = [](record_t& obj, auto fp, auto&&... a) -> decltype(auto) { return (obj.*fp)(std::forward(a)...); }; - return call(target, get_functor().f_ptr(), std::forward(params)...); + return hopper(target, get_functor().f_ptr(), std::forward(params)...); } }; } \ No newline at end of file From 7780b027ad8ac5253de53ffac7ab39e482754d7e Mon Sep 17 00:00:00 2001 From: neeraj Date: Mon, 22 Sep 2025 18:15:55 +0530 Subject: [PATCH 25/58] added type-safe access, code refined. --- .../src/ReflectedCallKnownReturn.cpp | 265 +++++++----------- .../src/ReflectedCallUnknownReturn.cpp | 14 +- RTLBenchmarkApp/src/StandardCall.cpp | 2 - RTLBenchmarkApp/src/main.cpp | 17 +- .../rtl/builder/SetupFunction.hpp | 5 +- .../rtl/builder/SetupMethod.hpp | 6 +- .../rtl/detail/inc/FunctorId.h | 19 ++ .../rtl/detail/inc/forward_decls.h | 3 + ReflectionTemplateLib/rtl/dispatch/lambda.h | 11 +- .../rtl/dispatch/lambda_method.h | 2 +- ReflectionTemplateLib/rtl/inc/Function.hpp | 5 +- ReflectionTemplateLib/rtl/inc/Method.hpp | 5 +- 12 files changed, 147 insertions(+), 207 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 9247b0a4..225fe6cc 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -1,6 +1,6 @@ -#include #include +#include #include "BenchMark.h" #include "ReflectedCallKnownReturn.h" @@ -20,256 +20,183 @@ namespace { static const rtl::lambda_function& getMessage_lambda = []() { - // No validation is performed internally and lambda - // will not return nullptr on signature mismatch. (by design) - return *(cxx::mirror().getFunction("getMessage")->get_lambda()); + auto lambda_ptr = cxx::mirror().getFunction("getMessage")->get_lambda(); + if(!lambda_ptr) { + std::cerr << "[0] error: return-type mismatch.\n"; + std::abort(); + } + return *lambda_ptr; }(); static const rtl::lambda_function& sendMessage_lambda = []() { - // No validation is performed internally and lambda - // will not return nullptr on signature mismatch. (by design) - return *(cxx::mirror().getFunction("sendMessage")->get_lambda()); + auto lambda_ptr = cxx::mirror().getFunction("sendMessage")->get_lambda(); + if(!lambda_ptr) { + std::cerr << "[1] error: return-type mismatch.\n"; + std::abort(); + } + return *lambda_ptr; + }(); static const rtl::lambda_method& getMessageOnNode_lambda = []() { - // No validation is performed internally and lambda - // will not return nullptr on signature mismatch. (by design) - return *(cxx::mirror().getRecord("Node")->getMethod("getMessage")->get_lambda()); + auto lambda_ptr = cxx::mirror().getRecord("Node")->getMethod("getMessage")->get_lambda(); + if(!lambda_ptr) { + std::cerr << "[2] error: return-type mismatch.\n"; + std::abort(); + } + return *lambda_ptr; }(); static const rtl::lambda_method& sendMessageOnNode_lambda = []() { - rtl::Record Node = cxx::mirror().getRecord("Node").value(); - // No validation is performed internally and lambda - // will not return nullptr on signature mismatch. (by design) - return *(cxx::mirror().getRecord("Node")->getMethod("sendMessage")->get_lambda()); + auto lambda_ptr = cxx::mirror().getRecord("Node")->getMethod("sendMessage")->get_lambda(); + if(!lambda_ptr) { + std::cerr << "[3] error: return-type mismatch.\n"; + std::abort(); + } + return *lambda_ptr; }(); } namespace { - static auto _test0 = []() + static auto functor_set = [](int n) { - if(!sendMessage_lambda.is_signature() || - !sendMessage_lambda.is_returning()) - { - std::cout << "[0] error: signature mismatch.\n"; - return false; + if(!sendMessage_lambda.is_returning()) { + std::cerr << "[0"<< n <<"] error: return-type mismatch.\n"; + std::abort(); } - return true; + // 'get_functor': No validation is performed internally and this function + // will not return nullptr on return_t mismatch. (by design). + return sendMessage_lambda.get_functor().f_ptr(); }; - static auto _test1 = []() + static auto method_set = [](int n) { - if(!sendMessageOnNode_lambda.is_signature() || - !sendMessageOnNode_lambda.is_returning()) - { - std::cout << "[1] error: signature mismatch.\n"; - return false; - } - return true; + if(!sendMessageOnNode_lambda.is_returning()) { + std::cerr << "[1"<< n <<"] error: return-type mismatch.\n"; + std::abort(); + } + // 'get_functor': No validation is performed internally and this function + // will not return nullptr on return_t mismatch. (by design). + return sendMessageOnNode_lambda.get_functor().f_ptr(); }; - static auto _test2 = []() + static auto functor_get = [](int n) { - if (!getMessage_lambda.is_signature() || - !getMessage_lambda.is_returning()) - { - std::cout << "[2] error: signature mismatch.\n"; - return false; + if (!getMessage_lambda.is_returning()) { + std::cerr << "[2"<< n <<"] error: return-type mismatch.\n"; + std::abort(); } - return true; + // 'get_functor': No validation is performed internally and this function + // will not return nullptr on return_t mismatch. (by design). + return getMessage_lambda.get_functor().f_ptr(); }; - static auto _test3 = []() + static auto method_get = [](int n) { - if (!getMessageOnNode_lambda.is_signature() || - !getMessageOnNode_lambda.is_returning()) + if (!getMessageOnNode_lambda.is_returning()) { - std::cout << "[3] error: signature mismatch.\n"; - return false; + std::cerr << "[3"<< n <<"] error: return-type mismatch.\n"; + std::abort(); } - return true; + // 'get_functor': No validation is performed internally and this function + // will not return nullptr on return_t mismatch. (by design). + return getMessageOnNode_lambda.get_functor().f_ptr(); }; -} - -void FunctionPointerCall::set(benchmark::State& state) -{ - static auto* functor = []() -> void(*)(bm::argStr_t) - { - // Must be checked: Passing an incorrect argument or return type is undefined behaviour. - if (sendMessage_lambda.is_returning() && sendMessage_lambda.is_signature()) - { - // No validation is performed internally and the function will not return nullptr on mismatch. - return sendMessage_lambda.get_functor().f_ptr(); - } - std::cout << "[4] error: signature mismatch.\n"; - return nullptr; - }(); - - for (auto _ : state) - { - if (functor) - { - (*functor)(bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done->c_str()); - } - } + static auto _new_line = []() { + std::cout << std::endl; + return 0; + }; } -void MethodFnPointerCall::set(benchmark::State& state) -{ - static bm::Node nodeObj; - static auto functor = []() -> void(bm::Node::*)(bm::argStr_t) - { - // Must be checked: Passing an incorrect argument or return type is undefined behaviour. - if (sendMessageOnNode_lambda.is_returning() && sendMessageOnNode_lambda.is_signature()) - { - // No validation is performed internally and the function will not return nullptr on mismatch. - return sendMessageOnNode_lambda.get_functor().f_ptr(); - } - std::cout << "[8] error: signature mismatch.\n"; - return nullptr; - }(); +void FunctionPointerCall::get(benchmark::State& state) +{ + static auto functor = functor_get(0); for (auto _ : state) { - if (functor) - { - (nodeObj.*functor)(bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done->c_str()); - } + benchmark::DoNotOptimize((*functor)(bm::g_longStr)); } } - void MethodFnPointerCall::get(benchmark::State& state) { static bm::Node nodeObj; - static auto functor = []() -> bm::retStr_t(bm::Node::*)(bm::argStr_t) - { - // Must be checked: Passing an incorrect argument or return type is undefined behaviour. - if (getMessageOnNode_lambda.is_returning() && getMessageOnNode_lambda.is_signature()) - { - // No validation is performed internally and the function will not return nullptr on mismatch. - return getMessageOnNode_lambda.get_functor().f_ptr(); - } - std::cout << "[9] error: signature mismatch.\n"; - return nullptr; - }(); - + static auto functor = method_get(0); for (auto _ : state) { - if (functor) - { - benchmark::DoNotOptimize((nodeObj.*functor)(bm::g_longStr)); - } + benchmark::DoNotOptimize((nodeObj.*functor)(bm::g_longStr)); } } - -void FunctionPointerCall::get(benchmark::State& state) +void FunctionPointerCall::set(benchmark::State& state) { - static auto* functor = []() -> bm::retStr_t(*)(bm::argStr_t) - { - // Must be checked: Passing an incorrect argument or return type is undefined behaviour. - if (getMessage_lambda.is_returning() && getMessage_lambda.is_signature()) - { - // No validation is performed internally and the function will not return nullptr on mismatch. - return getMessage_lambda.get_functor().f_ptr(); - } - std::cout << "[5] error: signature mismatch.\n"; - return nullptr; - }(); - + static auto _ = functor_set(0); + static auto functor = sendMessage_lambda.get_functor().f_ptr(); for (auto _ : state) { - if (functor) - { - benchmark::DoNotOptimize((*functor)(bm::g_longStr)); - } + (*functor)(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } - -void RtlReflectedCall::set(benchmark::State& state) +void MethodFnPointerCall::set(benchmark::State& state) { - static auto passed = _test0(); + static bm::Node nodeObj; + static auto functor = method_set(0); for (auto _ : state) { - if (passed) - { - sendMessage_lambda.hop(bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done->c_str()); - } + (nodeObj.*functor)(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } + void RtlReflectedCall::get(benchmark::State& state) { - static auto passed = _test2(); + static auto _=_new_line(); + static auto _test = functor_get(1); for (auto _: state) { - if (passed) - { - benchmark::DoNotOptimize(getMessage_lambda.hop(bm::g_longStr)); - } + benchmark::DoNotOptimize(getMessage_lambda.hop(bm::g_longStr)); } } - -void RtlReflectedMethodCall::set(benchmark::State& state) +void RtlReflectedMethodCall::get(benchmark::State& state) { static bm::Node nodeObj; - static auto functor = []() -> void(bm::Node::*)(bm::argStr_t) - { - // Must be checked: Passing an incorrect argument or return type is undefined behaviour. - if (sendMessageOnNode_lambda.is_returning() && sendMessageOnNode_lambda.is_signature()) - { - // No validation is performed internally and the function will not return nullptr on mismatch. - return sendMessageOnNode_lambda.get_functor().f_ptr(); - } - std::cout << "[6] error: signature mismatch.\n"; - return nullptr; - }(); - + static auto _test = method_get(1); for (auto _ : state) { - if (functor) - { - sendMessageOnNode_lambda.hop(nodeObj, bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done->c_str()); - } + benchmark::DoNotOptimize(getMessageOnNode_lambda.hop(nodeObj, bm::g_longStr)); } } +void RtlReflectedCall::set(benchmark::State& state) +{ + static auto _=_new_line(); + static auto _test = functor_set(1); + for (auto _ : state) + { + sendMessage_lambda.hop(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); + } +} -void RtlReflectedMethodCall::get(benchmark::State& state) +void RtlReflectedMethodCall::set(benchmark::State& state) { static bm::Node nodeObj; - static auto functor = []() -> bm::retStr_t(bm::Node::*)(bm::argStr_t) - { - // Must be checked: Passing an incorrect argument or return type is undefined behaviour. - if (getMessageOnNode_lambda.is_returning() && getMessageOnNode_lambda.is_signature()) - { - // No validation is performed internally and the function will not return nullptr on mismatch. - return getMessageOnNode_lambda.get_functor().f_ptr(); - } - std::cout << "[7] error: signature mismatch.\n"; - return nullptr; - }(); - + static auto _test = method_set(1); for (auto _ : state) { - if (functor) - { - benchmark::DoNotOptimize(getMessageOnNode_lambda.hop(nodeObj, bm::g_longStr)); - } + sendMessageOnNode_lambda.hop(nodeObj, bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } \ No newline at end of file diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index db9b2ee9..a73adb8e 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -36,7 +36,7 @@ namespace { auto [err, robj] = cxx::mirror().getRecord("Node")->create(); if (robj.isEmpty()) { - std::cout << "[_] error: " << rtl::to_string(err) << "\n"; + std::cout << "[x] error: " << rtl::to_string(err) << "\n"; } return std::move(robj); }(); @@ -89,8 +89,7 @@ void RtlReflectedCall_retUnknown::set(benchmark::State& state) static auto _ = _test0(); for (auto _ : state) { - auto error = SendMessage(bm::g_longStr).err; - benchmark::DoNotOptimize(error); + benchmark::DoNotOptimize(SendMessage(bm::g_longStr)); } } @@ -100,8 +99,7 @@ void RtlReflectedCall_retUnknown::get(benchmark::State& state) static auto _ = _test2(); for (auto _ : state) { - auto error = GetMessage(bm::g_longStr).err; - benchmark::DoNotOptimize(error); + benchmark::DoNotOptimize(GetMessage(bm::g_longStr)); } } @@ -111,8 +109,7 @@ void RtlReflectionMethodCall_retUnknown::set(benchmark::State& state) static auto _ = _test1(); for (auto _ : state) { - auto error = NodeSendMessage(nodeObj)(bm::g_longStr).err; - benchmark::DoNotOptimize(error); + benchmark::DoNotOptimize(NodeSendMessage(nodeObj)(bm::g_longStr)); } } @@ -122,7 +119,6 @@ void RtlReflectionMethodCall_retUnknown::get(benchmark::State& state) static auto _ = _test3(); for (auto _ : state) { - auto error = NodeGetMessage(nodeObj)(bm::g_longStr).err; - benchmark::DoNotOptimize(error); + benchmark::DoNotOptimize(NodeGetMessage(nodeObj)(bm::g_longStr)); } } \ No newline at end of file diff --git a/RTLBenchmarkApp/src/StandardCall.cpp b/RTLBenchmarkApp/src/StandardCall.cpp index 53294634..c8dad681 100644 --- a/RTLBenchmarkApp/src/StandardCall.cpp +++ b/RTLBenchmarkApp/src/StandardCall.cpp @@ -73,7 +73,6 @@ void StdFunctionCall::set(benchmark::State& state) void StdFunctionMethodCall::set(benchmark::State& state) { static bm::Node nodeObj; - static auto _=_new_line(); for (auto _: state) { bm::NodeSendMessage(nodeObj, bm::g_longStr); @@ -95,7 +94,6 @@ void StdFunctionCall::get(benchmark::State& state) void StdFunctionMethodCall::get(benchmark::State& state) { static bm::Node nodeObj; - static auto _=_new_line(); for (auto _: state) { benchmark::DoNotOptimize(bm::NodeGetMessage(nodeObj, bm::g_longStr)); diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index b9a7d869..eae49a1f 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -10,29 +10,24 @@ BENCHMARK(NativeCall::set); BENCHMARK(FunctionPointerCall::set); BENCHMARK(MethodFnPointerCall::set); -//BENCHMARK(ReflectedCallKnownReturn::set); -//BENCHMARK(ReflectedCallKnownReturn::set); - BENCHMARK(StdFunctionCall::set); -BENCHMARK(RtlReflectedCall::set); -BENCHMARK(RtlReflectedCall_retUnknown::set); - BENCHMARK(StdFunctionMethodCall::set); + +BENCHMARK(RtlReflectedCall::set); BENCHMARK(RtlReflectedMethodCall::set); +BENCHMARK(RtlReflectedCall_retUnknown::set); BENCHMARK(RtlReflectionMethodCall_retUnknown::set); BENCHMARK(NativeCall::get); BENCHMARK(FunctionPointerCall::get); BENCHMARK(MethodFnPointerCall::get); -//BENCHMARK(ReflectedMethodCallKnownReturn::get); BENCHMARK(StdFunctionCall::get); -BENCHMARK(RtlReflectedCall::get); -BENCHMARK(RtlReflectedCall_retUnknown::get); -//BENCHMARK(ReflectedMethodCallKnownReturn::get); - BENCHMARK(StdFunctionMethodCall::get); + +BENCHMARK(RtlReflectedCall::get); BENCHMARK(RtlReflectedMethodCall::get); +BENCHMARK(RtlReflectedCall_retUnknown::get); BENCHMARK(RtlReflectionMethodCall_retUnknown::get); namespace bm diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index 080ea460..d609cb83 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -30,7 +30,7 @@ namespace rtl { return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { - bool isFunctorGood = (pFunctor == pFunctorId.m_lambda->to_function<_signature...>()->template get_functor().f_ptr()); + bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_function<_signature...>()->template get_functor().f_ptr()); assert(isFunctorGood && "new type-id-system not working."); pFunctor(std::forward<_signature>(params)...); @@ -48,7 +48,8 @@ namespace rtl this is stored in _derivedType's (FunctorContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, _signature&&...params)-> Return { - bool isFunctorGood = (pFunctor == pFunctorId.m_lambda->to_function<_signature...>()->template get_functor<_returnType>().f_ptr()); + bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_function<_signature...>()->template get_functor<_returnType>().f_ptr()); + assert(isFunctorGood && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 1bf64725..ac4f83ca 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -34,7 +34,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isFunctorGood = (pFunctor == pFunctorId.m_lambda->to_method<_recordType, _signature...>()->template get_functor().f_ptr()); + bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor().f_ptr()); + assert(isFunctorGood && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { @@ -57,7 +58,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isFunctorGood = (pFunctor == pFunctorId.m_lambda->to_method<_recordType, _signature...>()->template get_functor<_returnType>().f_ptr()); + bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor<_returnType>().f_ptr()); + assert(isFunctorGood && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index 23fcd69f..a3de2455 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -15,6 +15,7 @@ #include "rtl_constants.h" #include "forward_decls.h" #include "lambda_method.h" +#include "lambda_function.h" namespace rtl::detail @@ -78,5 +79,23 @@ namespace rtl::detail m_lambdaIndex == pOther.m_lambdaIndex && m_signature == pOther.m_signature); } + + template + const dispatch::lambda_function<_signature...>* get_lambda_function() const + { + if(m_lambda->is_signature<_signature...>()) { + return m_lambda->to_function<_signature...>(); + } + return nullptr; + } + + template + const dispatch::lambda_method<_recordType, _signature...>* get_lambda_method() const + { + if(m_lambda->is_member<_recordType>() && m_lambda->is_signature<_signature...>()) { + return m_lambda->to_method<_recordType, _signature...>(); + } + return nullptr; + } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index 63456bd0..9d7b956a 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -31,6 +31,9 @@ namespace rtl template class FunctorContainer; + + template + class SetupMethod; } namespace cache diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index b2cfde79..7661a1cd 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -31,11 +31,7 @@ namespace rtl::dispatch template using method_t = lambda_method; - - public: - - GETTER_CREF(functor, _functor, m_functor); - + template constexpr const function_t* to_function() const { @@ -59,6 +55,9 @@ namespace rtl::dispatch return nullptr; } + public: + + GETTER_CREF(functor, _functor, m_functor); template constexpr bool is_returning() const @@ -78,5 +77,7 @@ namespace rtl::dispatch return (m_functor.m_recordId == detail::TypeId>::get() || m_functor.m_recordId == detail::TypeId>::get()); } + + friend detail::FunctorId; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index 1d7fd42c..2aee249a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -34,7 +34,7 @@ namespace rtl::dispatch :lambda(fptr) { } - // Unsafe: using an incorrect argument or return type is undefined behaviour. + // Unsafe: using an incorrect return type is undefined behaviour. // Not validated here and the function will not return nullptr on mismatch. (By Design) template [[nodiscard]] constexpr auto& get_functor() const diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index 56eea735..76fdb9a4 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -25,9 +25,8 @@ namespace rtl template const dispatch::lambda_function<_signature...>* Function::get_lambda(std::size_t pOverloadIndex) const { - if (pOverloadIndex < m_functorIds.size()) - { - return m_functorIds[pOverloadIndex].m_lambda->to_function<_signature...>(); + if (pOverloadIndex < m_functorIds.size()) { + return m_functorIds[pOverloadIndex].get_lambda_function<_signature...>(); } return nullptr; } diff --git a/ReflectionTemplateLib/rtl/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp index 57bdbab5..431154d8 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.hpp +++ b/ReflectionTemplateLib/rtl/inc/Method.hpp @@ -33,9 +33,8 @@ namespace rtl const dispatch::lambda_method<_recordType, _signature...>* Method::get_lambda(std::size_t pOverloadIndex) const { auto& functorIds = getFunctors(); - if (pOverloadIndex < functorIds.size()) - { - return functorIds[pOverloadIndex].m_lambda->to_method<_recordType, _signature...>(); + if (pOverloadIndex < functorIds.size()) { + return functorIds[pOverloadIndex].get_lambda_method<_recordType, _signature...>(); } return nullptr; } From 7bdc319ae7ba4990cb310389f7a57172c5827bbd Mon Sep 17 00:00:00 2001 From: neeraj Date: Mon, 22 Sep 2025 22:07:39 +0530 Subject: [PATCH 26/58] minor refactor. --- .../src/ReflectedCallKnownReturn.cpp | 18 +++++---- .../src/ReflectedCallKnownReturn.h | 20 +++++----- .../src/ReflectedCallUnknownReturn.cpp | 15 +++++-- .../src/ReflectedCallUnknownReturn.h | 12 +++--- RTLBenchmarkApp/src/StandardCall.cpp | 12 +++--- RTLBenchmarkApp/src/StandardCall.h | 12 +++--- RTLBenchmarkApp/src/main.cpp | 40 ++++++++++--------- .../rtl/builder/SetupFunction.hpp | 9 ++--- .../rtl/builder/SetupMethod.hpp | 18 ++++----- .../rtl/dispatch/lambda_function.h | 4 +- .../rtl/dispatch/lambda_method.h | 2 +- 11 files changed, 86 insertions(+), 76 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 225fe6cc..f5caeaaf 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -116,8 +116,9 @@ namespace -void FunctionPointerCall::get(benchmark::State& state) +void FunctionPointerCall::returnTypeNonVoid(benchmark::State& state) { + static auto _=_new_line(); static auto functor = functor_get(0); for (auto _ : state) { @@ -125,7 +126,7 @@ void FunctionPointerCall::get(benchmark::State& state) } } -void MethodFnPointerCall::get(benchmark::State& state) +void MethodFnPointerCall::returnTypeNonVoid(benchmark::State& state) { static bm::Node nodeObj; static auto functor = method_get(0); @@ -135,8 +136,9 @@ void MethodFnPointerCall::get(benchmark::State& state) } } -void FunctionPointerCall::set(benchmark::State& state) +void FunctionPointerCall::returnTypeVoid(benchmark::State& state) { + static auto __=_new_line(); static auto _ = functor_set(0); static auto functor = sendMessage_lambda.get_functor().f_ptr(); for (auto _ : state) @@ -146,7 +148,7 @@ void FunctionPointerCall::set(benchmark::State& state) } } -void MethodFnPointerCall::set(benchmark::State& state) +void MethodFnPointerCall::returnTypeVoid(benchmark::State& state) { static bm::Node nodeObj; static auto functor = method_set(0); @@ -159,7 +161,7 @@ void MethodFnPointerCall::set(benchmark::State& state) -void RtlReflectedCall::get(benchmark::State& state) +void ReflectedCallKnownReturn::typeNonVoid(benchmark::State& state) { static auto _=_new_line(); static auto _test = functor_get(1); @@ -169,7 +171,7 @@ void RtlReflectedCall::get(benchmark::State& state) } } -void RtlReflectedMethodCall::get(benchmark::State& state) +void ReflectedMethodCallKnownReturn::typeNonVoid(benchmark::State& state) { static bm::Node nodeObj; static auto _test = method_get(1); @@ -179,7 +181,7 @@ void RtlReflectedMethodCall::get(benchmark::State& state) } } -void RtlReflectedCall::set(benchmark::State& state) +void ReflectedCallKnownReturn::typeVoid(benchmark::State& state) { static auto _=_new_line(); static auto _test = functor_set(1); @@ -190,7 +192,7 @@ void RtlReflectedCall::set(benchmark::State& state) } } -void RtlReflectedMethodCall::set(benchmark::State& state) +void ReflectedMethodCallKnownReturn::typeVoid(benchmark::State& state) { static bm::Node nodeObj; static auto _test = method_set(1); diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h index e1f9c47a..a6a5a61d 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h @@ -2,33 +2,33 @@ #include -struct RtlReflectedCall +struct ReflectedCallKnownReturn { - static void set(benchmark::State& state); + static void typeVoid(benchmark::State& state); - static void get(benchmark::State& state); + static void typeNonVoid(benchmark::State& state); }; struct FunctionPointerCall { - static void set(benchmark::State& state); + static void returnTypeVoid(benchmark::State& state); - static void get(benchmark::State& state); + static void returnTypeNonVoid(benchmark::State& state); }; struct MethodFnPointerCall { - static void set(benchmark::State& state); + static void returnTypeVoid(benchmark::State& state); - static void get(benchmark::State& state); + static void returnTypeNonVoid(benchmark::State& state); }; -struct RtlReflectedMethodCall +struct ReflectedMethodCallKnownReturn { - static void set(benchmark::State& state); + static void typeVoid(benchmark::State& state); - static void get(benchmark::State& state); + static void typeNonVoid(benchmark::State& state); }; \ No newline at end of file diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index a73adb8e..ba82d409 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -80,12 +80,18 @@ namespace } return 0; }; + + static auto _new_line = []() { + std::cout << std::endl; + return 0; + }; } -void RtlReflectedCall_retUnknown::set(benchmark::State& state) +void ReflectedCallUnknownReturn::typeVoid(benchmark::State& state) { + static auto __=_new_line(); static auto _ = _test0(); for (auto _ : state) { @@ -94,8 +100,9 @@ void RtlReflectedCall_retUnknown::set(benchmark::State& state) } -void RtlReflectedCall_retUnknown::get(benchmark::State& state) +void ReflectedCallUnknownReturn::typeNonVoid(benchmark::State& state) { + static auto __=_new_line(); static auto _ = _test2(); for (auto _ : state) { @@ -104,7 +111,7 @@ void RtlReflectedCall_retUnknown::get(benchmark::State& state) } -void RtlReflectionMethodCall_retUnknown::set(benchmark::State& state) +void ReflectedMethodCallUnknownReturn::typeVoid(benchmark::State& state) { static auto _ = _test1(); for (auto _ : state) @@ -114,7 +121,7 @@ void RtlReflectionMethodCall_retUnknown::set(benchmark::State& state) } -void RtlReflectionMethodCall_retUnknown::get(benchmark::State& state) +void ReflectedMethodCallUnknownReturn::typeNonVoid(benchmark::State& state) { static auto _ = _test3(); for (auto _ : state) diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h index c2890430..9ceec026 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h @@ -2,17 +2,17 @@ #include -struct RtlReflectedCall_retUnknown +struct ReflectedCallUnknownReturn { - static void set(benchmark::State& state); + static void typeVoid(benchmark::State& state); - static void get(benchmark::State& state); + static void typeNonVoid(benchmark::State& state); }; -struct RtlReflectionMethodCall_retUnknown +struct ReflectedMethodCallUnknownReturn { - static void set(benchmark::State& state); + static void typeVoid(benchmark::State& state); - static void get(benchmark::State& state); + static void typeNonVoid(benchmark::State& state); }; \ No newline at end of file diff --git a/RTLBenchmarkApp/src/StandardCall.cpp b/RTLBenchmarkApp/src/StandardCall.cpp index c8dad681..53e14830 100644 --- a/RTLBenchmarkApp/src/StandardCall.cpp +++ b/RTLBenchmarkApp/src/StandardCall.cpp @@ -39,7 +39,7 @@ namespace bm } -void NativeCall::set(benchmark::State& state) +void NativeCall::returnTypeVoid(benchmark::State& state) { for (auto _: state) { @@ -49,7 +49,7 @@ void NativeCall::set(benchmark::State& state) } -void NativeCall::get(benchmark::State& state) +void NativeCall::returnTypeNonVoid(benchmark::State& state) { static auto _=_put_line(); for (auto _: state) @@ -59,7 +59,7 @@ void NativeCall::get(benchmark::State& state) } -void StdFunctionCall::set(benchmark::State& state) +void StdFunctionCall::returnTypeVoid(benchmark::State& state) { static auto _=_new_line(); for (auto _: state) @@ -70,7 +70,7 @@ void StdFunctionCall::set(benchmark::State& state) } -void StdFunctionMethodCall::set(benchmark::State& state) +void StdFunctionMethodCall::returnTypeVoid(benchmark::State& state) { static bm::Node nodeObj; for (auto _: state) @@ -81,7 +81,7 @@ void StdFunctionMethodCall::set(benchmark::State& state) } -void StdFunctionCall::get(benchmark::State& state) +void StdFunctionCall::returnTypeNonVoid(benchmark::State& state) { static auto _=_new_line(); for (auto _: state) @@ -91,7 +91,7 @@ void StdFunctionCall::get(benchmark::State& state) } -void StdFunctionMethodCall::get(benchmark::State& state) +void StdFunctionMethodCall::returnTypeNonVoid(benchmark::State& state) { static bm::Node nodeObj; for (auto _: state) diff --git a/RTLBenchmarkApp/src/StandardCall.h b/RTLBenchmarkApp/src/StandardCall.h index 76bd70f2..e6ca7b00 100644 --- a/RTLBenchmarkApp/src/StandardCall.h +++ b/RTLBenchmarkApp/src/StandardCall.h @@ -4,23 +4,23 @@ struct NativeCall { - static void set(benchmark::State& state); + static void returnTypeVoid(benchmark::State& state); - static void get(benchmark::State& state); + static void returnTypeNonVoid(benchmark::State& state); }; struct StdFunctionCall { - static void set(benchmark::State& state); + static void returnTypeVoid(benchmark::State& state); - static void get(benchmark::State& state); + static void returnTypeNonVoid(benchmark::State& state); }; struct StdFunctionMethodCall { - static void set(benchmark::State& state); + static void returnTypeVoid(benchmark::State& state); - static void get(benchmark::State& state); + static void returnTypeNonVoid(benchmark::State& state); }; \ No newline at end of file diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index eae49a1f..44119ff6 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -6,29 +6,33 @@ #include "ReflectedCallKnownReturn.h" #include "ReflectedCallUnknownReturn.h" -BENCHMARK(NativeCall::set); -BENCHMARK(FunctionPointerCall::set); -BENCHMARK(MethodFnPointerCall::set); +BENCHMARK(NativeCall::returnTypeVoid); -BENCHMARK(StdFunctionCall::set); -BENCHMARK(StdFunctionMethodCall::set); +BENCHMARK(FunctionPointerCall::returnTypeVoid); +BENCHMARK(MethodFnPointerCall::returnTypeVoid); -BENCHMARK(RtlReflectedCall::set); -BENCHMARK(RtlReflectedMethodCall::set); -BENCHMARK(RtlReflectedCall_retUnknown::set); -BENCHMARK(RtlReflectionMethodCall_retUnknown::set); +BENCHMARK(StdFunctionCall::returnTypeVoid); +BENCHMARK(StdFunctionMethodCall::returnTypeVoid); -BENCHMARK(NativeCall::get); -BENCHMARK(FunctionPointerCall::get); -BENCHMARK(MethodFnPointerCall::get); +BENCHMARK(ReflectedCallKnownReturn::typeVoid); +BENCHMARK(ReflectedMethodCallKnownReturn::typeVoid); -BENCHMARK(StdFunctionCall::get); -BENCHMARK(StdFunctionMethodCall::get); +BENCHMARK(ReflectedCallUnknownReturn::typeVoid); +BENCHMARK(ReflectedMethodCallUnknownReturn::typeVoid); -BENCHMARK(RtlReflectedCall::get); -BENCHMARK(RtlReflectedMethodCall::get); -BENCHMARK(RtlReflectedCall_retUnknown::get); -BENCHMARK(RtlReflectionMethodCall_retUnknown::get); +BENCHMARK(NativeCall::returnTypeNonVoid); + +BENCHMARK(FunctionPointerCall::returnTypeNonVoid); +BENCHMARK(MethodFnPointerCall::returnTypeNonVoid); + +BENCHMARK(StdFunctionCall::returnTypeNonVoid); +BENCHMARK(StdFunctionMethodCall::returnTypeNonVoid); + +BENCHMARK(ReflectedCallKnownReturn::typeNonVoid); +BENCHMARK(ReflectedMethodCallKnownReturn::typeNonVoid); + +BENCHMARK(ReflectedCallUnknownReturn::typeNonVoid); +BENCHMARK(ReflectedMethodCallUnknownReturn::typeNonVoid); namespace bm { diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index d609cb83..1677e692 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -30,8 +30,8 @@ namespace rtl { return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { - bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_function<_signature...>()->template get_functor().f_ptr()); - assert(isFunctorGood && "new type-id-system not working."); + // bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_function<_signature...>()->template get_functor().f_ptr()); + // assert(isFunctorGood && "new type-id-system not working."); pFunctor(std::forward<_signature>(params)...); return { error::None, RObject{} }; @@ -48,9 +48,8 @@ namespace rtl this is stored in _derivedType's (FunctorContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, _signature&&...params)-> Return { - bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_function<_signature...>()->template get_functor<_returnType>().f_ptr()); - - assert(isFunctorGood && "new type-id-system not working."); + // bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_function<_signature...>()->template get_functor<_returnType>().f_ptr()); + // assert(isFunctorGood && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index ac4f83ca..0fdead0c 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -34,9 +34,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor().f_ptr()); - - assert(isFunctorGood && "new type-id-system not working."); + // bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor().f_ptr()); + // assert(isFunctorGood && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -58,9 +57,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor<_returnType>().f_ptr()); - - assert(isFunctorGood && "new type-id-system not working."); + // bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor<_returnType>().f_ptr()); + // assert(isFunctorGood && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -103,8 +101,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isLambdaGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->get_functor().get_lambda()); - assert(isLambdaGood && "new type-id-system not working."); + // bool isLambdaGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->get_functor().get_lambda()); + // assert(isLambdaGood && "new type-id-system not working."); const _recordType& target = pTargetObj.view<_recordType>()->get(); (target.*pFunctor)(std::forward<_signature>(params)...); @@ -122,8 +120,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - bool isLambdaGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->get_functor().get_lambda()); - assert(isLambdaGood && "new type-id-system not working."); + // bool isLambdaGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->get_functor().get_lambda()); + // assert(isLambdaGood && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); //'target' is const and 'pFunctor' is const-member-function. diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 86bc612a..84397b1f 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -37,8 +37,8 @@ namespace rtl::dispatch template [[nodiscard]] constexpr auto& get_functor() const { - // Unchecked: using an incorrect argument or return type is undefined behaviour. - // No validation is performed and the function will not return nullptr on mismatch. (By Design) + // Unsafe: using an incorrect return type is undefined behaviour. + // Not validated here and the function will not return nullptr on mismatch. (By Design) return static_cast&>(m_functor); } diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index 2aee249a..bbab99b8 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -47,7 +47,7 @@ namespace rtl::dispatch { static_assert(is_args_t_ok, "Argument types don't match signature."); - constexpr auto hopper = [](record_t& obj, auto fp, auto&&... a) -> decltype(auto) { + constexpr auto hopper = [](auto& obj, auto fp, auto&&... a) -> decltype(auto) { return (obj.*fp)(std::forward(a)...); }; return hopper(target, get_functor().f_ptr(), std::forward(params)...); From a2330ba18a1d66e9efa6f12df3c25e3d0f08a7ef Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Tue, 23 Sep 2025 12:10:49 +0530 Subject: [PATCH 27/58] add safe acess api's to dispatch-interface. --- .../src/ReflectedCallKnownReturn.cpp | 141 +++++------------- .../src/ReflectedCallUnknownReturn.cpp | 56 +++++-- RTLBenchmarkApp/src/StandardCall.cpp | 2 +- .../rtl/detail/inc/FunctorId.h | 10 +- .../rtl/detail/inc/forward_decls.h | 6 +- ReflectionTemplateLib/rtl/dispatch/lambda.h | 15 +- .../rtl/dispatch/lambda_function.h | 57 ++++--- .../rtl/dispatch/lambda_method.h | 57 ++++--- ReflectionTemplateLib/rtl/inc/Function.h | 15 +- ReflectionTemplateLib/rtl/inc/Function.hpp | 24 ++- ReflectionTemplateLib/rtl/inc/Method.h | 16 +- ReflectionTemplateLib/rtl/inc/Method.hpp | 26 +++- ReflectionTemplateLib/rtl/rtl.h | 8 +- 13 files changed, 234 insertions(+), 199 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index f5caeaaf..704955fb 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -18,132 +18,62 @@ namespace cxx namespace { - static const rtl::lambda_function& getMessage_lambda = []() - { - auto lambda_ptr = cxx::mirror().getFunction("getMessage")->get_lambda(); - if(!lambda_ptr) { - std::cerr << "[0] error: return-type mismatch.\n"; - std::abort(); - } - return *lambda_ptr; - }(); + static const auto getMessage_functor = cxx::mirror().getFunction("getMessage")->args_t().return_t(); - static const rtl::lambda_function& sendMessage_lambda = []() - { - auto lambda_ptr = cxx::mirror().getFunction("sendMessage")->get_lambda(); - if(!lambda_ptr) { - std::cerr << "[1] error: return-type mismatch.\n"; - std::abort(); - } - return *lambda_ptr; + static const auto sendMessage_functor = cxx::mirror().getFunction("sendMessage")->args_t().return_t(); - }(); + static const auto getMessageOnNode_functor = cxx::mirror().getRecord("Node")->getMethod("getMessage")->args_t().return_t(); - static const rtl::lambda_method& getMessageOnNode_lambda = []() - { - auto lambda_ptr = cxx::mirror().getRecord("Node")->getMethod("getMessage")->get_lambda(); - if(!lambda_ptr) { - std::cerr << "[2] error: return-type mismatch.\n"; - std::abort(); - } - return *lambda_ptr; - }(); - - static const rtl::lambda_method& sendMessageOnNode_lambda = []() - { - auto lambda_ptr = cxx::mirror().getRecord("Node")->getMethod("sendMessage")->get_lambda(); - if(!lambda_ptr) { - std::cerr << "[3] error: return-type mismatch.\n"; - std::abort(); - } - return *lambda_ptr; - }(); + static const auto sendMessageOnNode_functor = cxx::mirror().getRecord("Node")->getMethod("sendMessage")->args_t().return_t(); } namespace { - static auto functor_set = [](int n) - { - if(!sendMessage_lambda.is_returning()) { - std::cerr << "[0"<< n <<"] error: return-type mismatch.\n"; - std::abort(); - } - // 'get_functor': No validation is performed internally and this function - // will not return nullptr on return_t mismatch. (by design). - return sendMessage_lambda.get_functor().f_ptr(); - }; - - static auto method_set = [](int n) - { - if(!sendMessageOnNode_lambda.is_returning()) { - std::cerr << "[1"<< n <<"] error: return-type mismatch.\n"; - std::abort(); - } - // 'get_functor': No validation is performed internally and this function - // will not return nullptr on return_t mismatch. (by design). - return sendMessageOnNode_lambda.get_functor().f_ptr(); - }; - - static auto functor_get = [](int n) - { - if (!getMessage_lambda.is_returning()) { - std::cerr << "[2"<< n <<"] error: return-type mismatch.\n"; - std::abort(); - } - // 'get_functor': No validation is performed internally and this function - // will not return nullptr on return_t mismatch. (by design). - return getMessage_lambda.get_functor().f_ptr(); + static auto _new_line = []() { + std::cout << std::endl; + return 0; }; - static auto method_get = [](int n) + template + static bool test(const T& functor, int n) { - if (!getMessageOnNode_lambda.is_returning()) - { - std::cerr << "[3"<< n <<"] error: return-type mismatch.\n"; + if (!functor.is_valid()) { + std::cerr << "[" << n << "] error: functor not valid, return-type or signature mismatch.\n"; std::abort(); } - // 'get_functor': No validation is performed internally and this function - // will not return nullptr on return_t mismatch. (by design). - return getMessageOnNode_lambda.get_functor().f_ptr(); - }; - - static auto _new_line = []() { - std::cout << std::endl; - return 0; - }; + return true; + } } - void FunctionPointerCall::returnTypeNonVoid(benchmark::State& state) { static auto _=_new_line(); - static auto functor = functor_get(0); + static auto is_ok = test(getMessage_functor, 0); for (auto _ : state) { - benchmark::DoNotOptimize((*functor)(bm::g_longStr)); + benchmark::DoNotOptimize((getMessage_functor.f_ptr())(bm::g_longStr)); } } void MethodFnPointerCall::returnTypeNonVoid(benchmark::State& state) { static bm::Node nodeObj; - static auto functor = method_get(0); + static auto is_ok = test(getMessageOnNode_functor, 1); for (auto _ : state) { - benchmark::DoNotOptimize((nodeObj.*functor)(bm::g_longStr)); + benchmark::DoNotOptimize((nodeObj.*getMessageOnNode_functor.f_ptr())(bm::g_longStr)); } } void FunctionPointerCall::returnTypeVoid(benchmark::State& state) { - static auto __=_new_line(); - static auto _ = functor_set(0); - static auto functor = sendMessage_lambda.get_functor().f_ptr(); + static auto _ = _new_line(); + static auto is_ok = test(sendMessage_functor, 2); for (auto _ : state) { - (*functor)(bm::g_longStr); + (sendMessage_functor.f_ptr())(bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } @@ -151,11 +81,14 @@ void FunctionPointerCall::returnTypeVoid(benchmark::State& state) void MethodFnPointerCall::returnTypeVoid(benchmark::State& state) { static bm::Node nodeObj; - static auto functor = method_set(0); + static auto is_ok = test(getMessageOnNode_functor, 2); for (auto _ : state) { - (nodeObj.*functor)(bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done->c_str()); + if (sendMessageOnNode_functor.is_valid()) + { + (nodeObj.*sendMessageOnNode_functor.f_ptr())(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); + } } } @@ -163,31 +96,31 @@ void MethodFnPointerCall::returnTypeVoid(benchmark::State& state) void ReflectedCallKnownReturn::typeNonVoid(benchmark::State& state) { - static auto _=_new_line(); - static auto _test = functor_get(1); - for (auto _: state) + static auto _ = _new_line(); + static auto is_ok = test(getMessage_functor, 3); + for (auto _ : state) { - benchmark::DoNotOptimize(getMessage_lambda.hop(bm::g_longStr)); + benchmark::DoNotOptimize(getMessage_functor(bm::g_longStr)); } } void ReflectedMethodCallKnownReturn::typeNonVoid(benchmark::State& state) { static bm::Node nodeObj; - static auto _test = method_get(1); + static auto is_ok = test(getMessageOnNode_functor, 4); for (auto _ : state) { - benchmark::DoNotOptimize(getMessageOnNode_lambda.hop(nodeObj, bm::g_longStr)); + benchmark::DoNotOptimize(getMessageOnNode_functor(nodeObj, bm::g_longStr)); } } void ReflectedCallKnownReturn::typeVoid(benchmark::State& state) { - static auto _=_new_line(); - static auto _test = functor_set(1); + static auto _ = _new_line(); + static auto is_ok = test(sendMessage_functor, 0); for (auto _ : state) { - sendMessage_lambda.hop(bm::g_longStr); + sendMessage_functor(bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } @@ -195,10 +128,10 @@ void ReflectedCallKnownReturn::typeVoid(benchmark::State& state) void ReflectedMethodCallKnownReturn::typeVoid(benchmark::State& state) { static bm::Node nodeObj; - static auto _test = method_set(1); + static auto is_ok = test(sendMessageOnNode_functor, 5); for (auto _ : state) { - sendMessageOnNode_lambda.hop(nodeObj, bm::g_longStr); + sendMessageOnNode_functor(nodeObj, bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } \ No newline at end of file diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index ba82d409..760b7734 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -14,27 +14,65 @@ namespace { static rtl::Function GetMessage = []() { - return *(cxx::mirror().getFunction("getMessage")); + std::optional function = cxx::mirror().getFunction("getMessage"); + if (!function) { + std::cerr << "[0] error: function 'getMessage' not found.\n"; + std::abort(); + } + return *function; }(); static rtl::Function SendMessage = []() { - return *(cxx::mirror().getFunction("sendMessage")); + std::optional function = cxx::mirror().getFunction("sendMessage"); + if (!function) { + std::cerr << "[1] error: function 'sendMessage' not found.\n"; + std::abort(); + } + return *function; }(); static rtl::Method NodeGetMessage = []() { - return *(cxx::mirror().getRecord("Node")->getMethod("getMessage")); + std::optional Node = cxx::mirror().getRecord("Node"); + if (!Node) { + std::cerr << "[x] error: record 'Node' not found.\n"; + std::abort(); + } + + std::optional method = Node->getMethod("getMessage"); + if (!method) { + std::cerr << "[2] error: method 'Node::getMessage' not found.\n"; + std::abort(); + } + return *method; }(); static rtl::Method NodeSendMessage = []() { - return *(cxx::mirror().getRecord("Node")->getMethod("sendMessage")); + std::optional Node = cxx::mirror().getRecord("Node"); + if (!Node) { + std::cerr << "[x] error: record 'Node' not found.\n"; + std::abort(); + } + + std::optional method = Node->getMethod("sendMessage"); + if (!method) { + std::cerr << "[3] error: method 'Node::sendMessage' not found.\n"; + std::abort(); + } + return *method; }(); static const rtl::RObject nodeObj = []() { - auto [err, robj] = cxx::mirror().getRecord("Node")->create(); + std::optional Node = cxx::mirror().getRecord("Node"); + if (!Node) { + std::cerr << "[x] error: record 'Node' not found.\n"; + std::abort(); + } + + auto [err, robj] = Node->create(); if (robj.isEmpty()) { std::cout << "[x] error: " << rtl::to_string(err) << "\n"; } @@ -49,7 +87,7 @@ namespace { auto err = SendMessage(bm::g_longStr).err; if (err != rtl::error::None) { - std::cout << "[0] error: " << rtl::to_string(err) << "\n"; + std::cout << "[00] error: " << rtl::to_string(err) << "\n"; } return 0; }; @@ -58,7 +96,7 @@ namespace { auto err = NodeSendMessage(nodeObj)(bm::g_longStr).err; if (err != rtl::error::None) { - std::cout << "[1] error: " << rtl::to_string(err) << "\n"; + std::cout << "[01] error: " << rtl::to_string(err) << "\n"; } return 0; }; @@ -67,7 +105,7 @@ namespace { auto err = GetMessage(bm::g_longStr).err; if (err != rtl::error::None) { - std::cout << "[2] error: " << rtl::to_string(err) << "\n"; + std::cout << "[02] error: " << rtl::to_string(err) << "\n"; } return 0; }; @@ -76,7 +114,7 @@ namespace { auto err = NodeGetMessage(nodeObj)(bm::g_longStr).err; if (err != rtl::error::None) { - std::cout << "[3] error: " << rtl::to_string(err) << "\n"; + std::cout << "[03] error: " << rtl::to_string(err) << "\n"; } return 0; }; diff --git a/RTLBenchmarkApp/src/StandardCall.cpp b/RTLBenchmarkApp/src/StandardCall.cpp index 53e14830..d79c3d44 100644 --- a/RTLBenchmarkApp/src/StandardCall.cpp +++ b/RTLBenchmarkApp/src/StandardCall.cpp @@ -10,7 +10,7 @@ namespace { static auto _put_line = []() { std::cout << "----------------------------------------" - "------------------------------------------" << std::endl; + "------------------------------------------------" << std::endl; return 0; }; diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index a3de2455..bd919b1a 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -83,19 +83,13 @@ namespace rtl::detail template const dispatch::lambda_function<_signature...>* get_lambda_function() const { - if(m_lambda->is_signature<_signature...>()) { - return m_lambda->to_function<_signature...>(); - } - return nullptr; + return m_lambda->to_function<_signature...>(); } template const dispatch::lambda_method<_recordType, _signature...>* get_lambda_method() const { - if(m_lambda->is_member<_recordType>() && m_lambda->is_signature<_signature...>()) { - return m_lambda->to_method<_recordType, _signature...>(); - } - return nullptr; + return m_lambda->to_method<_recordType, _signature...>(); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index 9d7b956a..ac9e6df5 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -24,7 +24,7 @@ namespace rtl class Method; class CxxMirror; - + namespace detail { struct FunctorId; @@ -52,10 +52,10 @@ namespace rtl struct lambda; template - class lambda_function; + struct lambda_function; template - class lambda_method; + struct lambda_method; template struct function_ptr; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index 7661a1cd..36a3ef0c 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -35,24 +35,13 @@ namespace rtl::dispatch template constexpr const function_t* to_function() const { - const std::size_t typeId = detail::TypeId...>>::get(); - if (typeId == m_functor.m_signatureId) - { - return static_cast*>(this); - } - return nullptr; + return static_cast*>(this); } template constexpr const method_t* to_method() const { - std::size_t recordId = detail::TypeId::get(); - std::size_t typeId = detail::TypeId...>>::get(); - if (typeId == m_functor.m_signatureId && recordId == m_functor.m_recordId) - { - return static_cast*>(this); - } - return nullptr; + return static_cast*>(this); } public: diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 84397b1f..a09b9788 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -17,40 +17,53 @@ namespace rtl::dispatch { template - class lambda_function: public lambda + struct lambda_function: public lambda { template using fptr_t = typename function_ptr::functor_t; - template - static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - - template - static constexpr bool noexcept_v = noexcept(std::declval>()(std::declval()...)); - - public: - lambda_function(const functor& fptr) noexcept :lambda(fptr) { } template - [[nodiscard]] constexpr auto& get_functor() const + struct hopper { - // Unsafe: using an incorrect return type is undefined behaviour. - // Not validated here and the function will not return nullptr on mismatch. (By Design) - return static_cast&>(m_functor); - } + constexpr auto f_ptr() const { + return m_functor; + } - template - [[nodiscard]] constexpr decltype(auto) hop(args_t&&...params) const noexcept(noexcept_v) - { - static_assert(is_args_t_ok, "Argument types don't match signature."); + constexpr auto is_valid() const { + return (m_functor != nullptr); + } + + template + [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept(noexcept_v) + { + static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + return (*m_functor)(std::forward(params)...); + } - constexpr auto hopper = [](auto fp, auto&&... a) -> decltype(auto) { - return (*fp)(std::forward(a)...); - }; - return hopper(get_functor().f_ptr(), std::forward(params)...); + const fptr_t m_functor = nullptr; + + private: + + template + static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; + + template + static constexpr bool noexcept_v = noexcept(std::declval>()(std::declval()...)); + }; + + template + [[nodiscard]] constexpr const hopper get_hopper() const + { + if (m_functor.m_returnId == detail::TypeId::get()) + { + fptr_t func_ptr = (static_cast&>(m_functor)).f_ptr(); + return hopper{ func_ptr }; + } + return hopper(); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index bbab99b8..241ecc31 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -17,40 +17,57 @@ namespace rtl::dispatch { template - class lambda_method : public lambda + struct lambda_method : public lambda { template using fptr_t = typename method_ptr::functor_t; - template - static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - - template - static constexpr bool noexcept_v = noexcept((std::declval().*std::declval>())(std::declval()...)); - public: lambda_method(const functor& fptr) noexcept :lambda(fptr) { } - // Unsafe: using an incorrect return type is undefined behaviour. - // Not validated here and the function will not return nullptr on mismatch. (By Design) + template - [[nodiscard]] constexpr auto& get_functor() const + struct hopper { - return static_cast&>(m_functor); - } + constexpr auto f_ptr() const { + return m_functor; + } + + constexpr auto is_valid() const { + return (m_functor != nullptr); + } + + template + [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept(noexcept_v) + { + static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + return (target.*m_functor)(std::forward(params)...); + } - template - [[nodiscard]] constexpr decltype(auto) hop(record_t& target, args_t&& ...params) const noexcept(noexcept_v) + const fptr_t m_functor = nullptr; + + private: + + template + static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; + + template + static constexpr bool noexcept_v = noexcept((std::declval().*std::declval>())(std::declval()...)); + }; + + + template + [[nodiscard]] constexpr const hopper get_hopper() const { - static_assert(is_args_t_ok, "Argument types don't match signature."); - - constexpr auto hopper = [](auto& obj, auto fp, auto&&... a) -> decltype(auto) { - return (obj.*fp)(std::forward(a)...); - }; - return hopper(target, get_functor().f_ptr(), std::forward(params)...); + if (m_functor.m_returnId == detail::TypeId::get()) + { + fptr_t func_ptr = (static_cast&>(m_functor)).f_ptr(); + return hopper{ func_ptr }; + } + return hopper(); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 1df345be..ac35efe2 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -89,15 +89,24 @@ namespace rtl { Function& operator=(Function&&) = default; Function& operator=(const Function&) = default; + template + struct Hopper + { + const dispatch::lambda_function<_signature...>* m_lambda = nullptr; + + template + constexpr const dispatch::lambda_function<_signature...>::hopper<_returnType> return_t() const; + }; + + template + const Hopper<_signature...> args_t() const; + //indicates if a functor associated with it takes zero arguments. bool hasSignature() const; template bool hasSignature() const; - template - const dispatch::lambda_function<_signature...>* get_lambda(std::size_t pOverloadIndex = 0) const; - template Return operator()(_args&&...params) const noexcept; diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index 76fdb9a4..f07640c1 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -23,14 +23,30 @@ namespace rtl } template - const dispatch::lambda_function<_signature...>* Function::get_lambda(std::size_t pOverloadIndex) const + const Function::Hopper<_signature...> Function::args_t() const { - if (pOverloadIndex < m_functorIds.size()) { - return m_functorIds[pOverloadIndex].get_lambda_function<_signature...>(); + for (auto& functorId : m_functorIds) + { + if (functorId.m_lambda->is_signature<_signature...>()) [[likely]] { + return { functorId.get_lambda_function<_signature...>() }; + } } - return nullptr; + return Hopper<_signature...>(); } + + template + template + inline constexpr const dispatch::lambda_function<_signature...>::hopper<_returnType> + Function::Hopper<_signature...>::return_t() const + { + if (m_lambda != nullptr && m_lambda->is_returning<_returnType>()) { + return m_lambda->get_hopper<_returnType>(); + } + return dispatch::lambda_function<_signature...>::template hopper<_returnType>(); + } + + /* @method: hasSignature<...>() @param: set of arguments, explicitly specified as template parameter. @return: bool, if the functor associated with this object is of certain signature or not. diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index a3b551b3..166c9790 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -56,6 +56,19 @@ namespace rtl { GETTER_BOOL(Const, (getQualifier() == detail::methodQ::Const)); + + template + struct Hopper + { + const dispatch::lambda_method<_recordType, _signature...>* m_lambda = nullptr; + + template + constexpr const dispatch::lambda_method<_recordType, _signature...>::hopper<_returnType> return_t() const; + }; + + template + const Hopper<_recordType, _signature...> args_t() const; + //indicates if a particular set of arguments accepted by the functor associated with it. template bool hasSignature() const; @@ -66,9 +79,6 @@ namespace rtl { template const detail::NonConstInvoker<_signature...> bind(constCast&& pTarget) const; - template - const dispatch::lambda_method<_recordType, _signature...>* get_lambda(std::size_t pOverloadIndex = 0) const; - /* @method: operator()() @return: lambda * accepts no arguments for 'target', since associated functor is static-member-functions. diff --git a/ReflectionTemplateLib/rtl/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp index 431154d8..b354bda1 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.hpp +++ b/ReflectionTemplateLib/rtl/inc/Method.hpp @@ -30,13 +30,29 @@ namespace rtl template - const dispatch::lambda_method<_recordType, _signature...>* Method::get_lambda(std::size_t pOverloadIndex) const + const Method::Hopper<_recordType, _signature...> Method::args_t() const { - auto& functorIds = getFunctors(); - if (pOverloadIndex < functorIds.size()) { - return functorIds[pOverloadIndex].get_lambda_method<_recordType, _signature...>(); + for (auto& functorId : getFunctorIds()) + { + if (functorId.m_lambda->is_member<_recordType>() && + functorId.m_lambda->is_signature<_signature...>()) [[likely]] + { + return { functorId.get_lambda_method<_recordType, _signature...>() }; + } + } + return Hopper<_recordType, _signature...>(); + } + + + template + template + inline constexpr const dispatch::lambda_method<_recordType, _signature...>::hopper<_returnType> + Method::Hopper<_recordType, _signature...>::return_t() const + { + if (m_lambda != nullptr && m_lambda->is_returning<_returnType>()) { + return m_lambda->get_hopper<_returnType>(); } - return nullptr; + return dispatch::lambda_method<_recordType, _signature...>::template hopper<_returnType>(); } diff --git a/ReflectionTemplateLib/rtl/rtl.h b/ReflectionTemplateLib/rtl/rtl.h index a21b849a..e8196fc7 100644 --- a/ReflectionTemplateLib/rtl/rtl.h +++ b/ReflectionTemplateLib/rtl/rtl.h @@ -104,9 +104,9 @@ namespace rtl { - template - using lambda_function = dispatch::lambda_function; + template + using function_ptr = dispatch::lambda_function::template hopper; - template - using lambda_method = dispatch::lambda_method; + template + using method_ptr = dispatch::lambda_method::template hopper; } \ No newline at end of file From 7d1ef56f60b032a863d048f1647a0910b8774ea7 Mon Sep 17 00:00:00 2001 From: neeraj Date: Tue, 23 Sep 2025 16:59:20 +0530 Subject: [PATCH 28/58] fixed nested-template fiasco that clang couldn't handle. --- .../src/ReflectedCallKnownReturn.cpp | 56 +++++++++++++- .../rtl/detail/inc/forward_decls.h | 6 ++ .../rtl/dispatch/lambda_function.h | 73 ++++++++++-------- .../rtl/dispatch/lambda_method.h | 76 ++++++++++--------- ReflectionTemplateLib/rtl/inc/Function.h | 6 +- ReflectionTemplateLib/rtl/inc/Function.hpp | 13 ++-- ReflectionTemplateLib/rtl/inc/Method.h | 6 +- ReflectionTemplateLib/rtl/inc/Method.hpp | 13 ++-- ReflectionTemplateLib/rtl/rtl.h | 12 +-- 9 files changed, 157 insertions(+), 104 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 704955fb..ca19a74a 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -1,8 +1,10 @@ +#include #include #include #include "BenchMark.h" +#include "Function.h" #include "ReflectedCallKnownReturn.h" @@ -18,13 +20,59 @@ namespace cxx namespace { - static const auto getMessage_functor = cxx::mirror().getFunction("getMessage")->args_t().return_t(); + static const auto getMessage_functor = []() + { + std::optional function = cxx::mirror().getFunction("getMessage"); + if(!function) + { + std::cerr << "[00] error: function 'getMessage' not found.\n"; + std::abort(); + } + return function->args_t().return_t(); + }(); + + static const auto sendMessage_functor = []() + { + std::optional sendMessage = cxx::mirror().getFunction("sendMessage"); + if(!sendMessage) + { + std::cerr << "[01] error: function 'sendMessage' not found.\n"; + std::abort(); + } + return sendMessage->args_t().return_t(); + }(); + + static const auto getMessageOnNode_functor = []() + { + std::optional Node = cxx::mirror().getRecord("Node"); + if (!Node) { + std::cerr << "[x] error: record 'Node' not found.\n"; + std::abort(); + } - static const auto sendMessage_functor = cxx::mirror().getFunction("sendMessage")->args_t().return_t(); + std::optional method = Node->getMethod("getMessage"); + if (!method) { + std::cerr << "[02] error: method 'Node::getMessage' not found.\n"; + std::abort(); + } + return method->args_t().return_t(); + }(); - static const auto getMessageOnNode_functor = cxx::mirror().getRecord("Node")->getMethod("getMessage")->args_t().return_t(); + static const auto sendMessageOnNode_functor = []() + { + std::optional Node = cxx::mirror().getRecord("Node"); + if (!Node) { + std::cerr << "[x] error: record 'Node' not found.\n"; + std::abort(); + } - static const auto sendMessageOnNode_functor = cxx::mirror().getRecord("Node")->getMethod("sendMessage")->args_t().return_t(); + std::optional method = Node->getMethod("sendMessage"); + if (!method) { + std::cerr << "[3] error: method 'Node::sendMessage' not found.\n"; + std::abort(); + } + return method->args_t().return_t(); + }(); } diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index ac9e6df5..a755fb9c 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -25,6 +25,12 @@ namespace rtl class CxxMirror; + template + struct function_hop; + + template + struct method_hop; + namespace detail { struct FunctorId; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index a09b9788..77587425 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -14,56 +14,63 @@ #include "lambda.h" #include "function_ptr.h" -namespace rtl::dispatch +namespace rtl { - template - struct lambda_function: public lambda + template + struct function_hop { - template - using fptr_t = typename function_ptr::functor_t; + using fptr_t = return_t(*)(signature_ts...); - lambda_function(const functor& fptr) noexcept - :lambda(fptr) - { } + const fptr_t m_functor = nullptr; - template - struct hopper + constexpr auto f_ptr() const { + return m_functor; + } + + constexpr auto is_valid() const { + return (m_functor != nullptr); + } + + template + [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept(noexcept_v) { - constexpr auto f_ptr() const { - return m_functor; - } + static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + return (*m_functor)(std::forward(params)...); + } - constexpr auto is_valid() const { - return (m_functor != nullptr); - } - template - [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept(noexcept_v) - { - static_assert(is_args_t_ok, "Argument types don't match the expected signature."); - return (*m_functor)(std::forward(params)...); - } + private: - const fptr_t m_functor = nullptr; + template + static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - private: + template + static constexpr bool noexcept_v = noexcept(std::declval()(std::declval()...)); + }; +} - template - static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; +namespace rtl::dispatch +{ + template + struct lambda_function: public lambda + { + template + using hopper_t = function_hop; - template - static constexpr bool noexcept_v = noexcept(std::declval>()(std::declval()...)); - }; + lambda_function(const functor& p_functor) noexcept + :lambda(p_functor) + { } template - [[nodiscard]] constexpr const hopper get_hopper() const + constexpr const hopper_t get_hopper() const { if (m_functor.m_returnId == detail::TypeId::get()) { - fptr_t func_ptr = (static_cast&>(m_functor)).f_ptr(); - return hopper{ func_ptr }; + return hopper_t { + static_cast&>(m_functor).f_ptr() + }; } - return hopper(); + return hopper_t(); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index 241ecc31..d8cec377 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -14,60 +14,64 @@ #include "lambda.h" #include "method_ptr.h" -namespace rtl::dispatch + +namespace rtl { - template - struct lambda_method : public lambda + template + struct method_hop { - template - using fptr_t = typename method_ptr::functor_t; + using fptr_t = return_t (record_t::*)(signature_ts...); - public: + const fptr_t m_functor = nullptr; - lambda_method(const functor& fptr) noexcept - :lambda(fptr) - { } + constexpr auto f_ptr() const { + return m_functor; + } + constexpr auto is_valid() const { + return (m_functor != nullptr); + } - template - struct hopper + template + [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept(noexcept_v) { - constexpr auto f_ptr() const { - return m_functor; - } - - constexpr auto is_valid() const { - return (m_functor != nullptr); - } - - template - [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept(noexcept_v) - { - static_assert(is_args_t_ok, "Argument types don't match the expected signature."); - return (target.*m_functor)(std::forward(params)...); - } + static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + return (target.*m_functor)(std::forward(params)...); + } - const fptr_t m_functor = nullptr; + private: + + template + static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - private: + template + static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); + }; +} - template - static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - template - static constexpr bool noexcept_v = noexcept((std::declval().*std::declval>())(std::declval()...)); - }; +namespace rtl::dispatch +{ + template + struct lambda_method : public lambda + { + template + using hopper_t = method_hop; + lambda_method(const functor& p_functor) noexcept + :lambda(p_functor) + { } template - [[nodiscard]] constexpr const hopper get_hopper() const + constexpr const hopper_t get_hopper() const { if (m_functor.m_returnId == detail::TypeId::get()) { - fptr_t func_ptr = (static_cast&>(m_functor)).f_ptr(); - return hopper{ func_ptr }; + return hopper_t { + static_cast&>(m_functor).f_ptr() + }; } - return hopper(); + return hopper_t(); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index ac35efe2..2371f9b0 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -90,16 +90,16 @@ namespace rtl { Function& operator=(const Function&) = default; template - struct Hopper + struct HopBuilder { const dispatch::lambda_function<_signature...>* m_lambda = nullptr; template - constexpr const dispatch::lambda_function<_signature...>::hopper<_returnType> return_t() const; + constexpr const function_hop<_returnType(_signature...)> return_t() const; }; template - const Hopper<_signature...> args_t() const; + const HopBuilder<_signature...> args_t() const; //indicates if a functor associated with it takes zero arguments. bool hasSignature() const; diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index f07640c1..49650789 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -23,7 +23,7 @@ namespace rtl } template - const Function::Hopper<_signature...> Function::args_t() const + const Function::HopBuilder<_signature...> Function::args_t() const { for (auto& functorId : m_functorIds) { @@ -31,19 +31,18 @@ namespace rtl return { functorId.get_lambda_function<_signature...>() }; } } - return Hopper<_signature...>(); + return HopBuilder<_signature...>(); } template template - inline constexpr const dispatch::lambda_function<_signature...>::hopper<_returnType> - Function::Hopper<_signature...>::return_t() const + inline constexpr const function_hop<_returnType(_signature...)> Function::HopBuilder<_signature...>::return_t() const { - if (m_lambda != nullptr && m_lambda->is_returning<_returnType>()) { - return m_lambda->get_hopper<_returnType>(); + if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) { + return m_lambda->template get_hopper<_returnType>(); } - return dispatch::lambda_function<_signature...>::template hopper<_returnType>(); + return function_hop<_returnType(_signature...)>(); } diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index 166c9790..4e46f80b 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -58,16 +58,16 @@ namespace rtl { template - struct Hopper + struct HopBuilder { const dispatch::lambda_method<_recordType, _signature...>* m_lambda = nullptr; template - constexpr const dispatch::lambda_method<_recordType, _signature...>::hopper<_returnType> return_t() const; + constexpr const method_hop<_returnType (_recordType::*)(_signature...)> return_t() const; }; template - const Hopper<_recordType, _signature...> args_t() const; + const HopBuilder<_recordType, _signature...> args_t() const; //indicates if a particular set of arguments accepted by the functor associated with it. template diff --git a/ReflectionTemplateLib/rtl/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp index b354bda1..fb88da15 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.hpp +++ b/ReflectionTemplateLib/rtl/inc/Method.hpp @@ -30,7 +30,7 @@ namespace rtl template - const Method::Hopper<_recordType, _signature...> Method::args_t() const + const Method::HopBuilder<_recordType, _signature...> Method::args_t() const { for (auto& functorId : getFunctorIds()) { @@ -40,19 +40,18 @@ namespace rtl return { functorId.get_lambda_method<_recordType, _signature...>() }; } } - return Hopper<_recordType, _signature...>(); + return HopBuilder<_recordType, _signature...>(); } template template - inline constexpr const dispatch::lambda_method<_recordType, _signature...>::hopper<_returnType> - Method::Hopper<_recordType, _signature...>::return_t() const + inline constexpr const method_hop<_returnType (_recordType::*)(_signature...)> Method::HopBuilder<_recordType, _signature...>::return_t() const { - if (m_lambda != nullptr && m_lambda->is_returning<_returnType>()) { - return m_lambda->get_hopper<_returnType>(); + if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) { + return m_lambda->template get_hopper<_returnType>(); } - return dispatch::lambda_method<_recordType, _signature...>::template hopper<_returnType>(); + return method_hop<_returnType (_recordType::*)(_signature...)>(); } diff --git a/ReflectionTemplateLib/rtl/rtl.h b/ReflectionTemplateLib/rtl/rtl.h index e8196fc7..d4185e61 100644 --- a/ReflectionTemplateLib/rtl/rtl.h +++ b/ReflectionTemplateLib/rtl/rtl.h @@ -99,14 +99,4 @@ * * Declared in namespace rtl. */ -#include "CxxMirror.hpp" - - -namespace rtl { - - template - using function_ptr = dispatch::lambda_function::template hopper; - - template - using method_ptr = dispatch::lambda_method::template hopper; -} \ No newline at end of file +#include "CxxMirror.hpp" \ No newline at end of file From 0f8f46fa707ff8a5c229914054950e34283bb8e3 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Tue, 23 Sep 2025 20:11:26 +0530 Subject: [PATCH 29/58] refined dispatch apis, added- rtl::function, rtl::method. --- .../src/ReflectedCallKnownReturn.cpp | 72 +++++++++---------- .../rtl/detail/inc/FunctionCaller.h | 30 ++++++-- .../rtl/detail/inc/FunctionCaller.hpp | 37 +++++++++- .../rtl/detail/inc/MethodInvoker.h | 22 ++++++ .../rtl/detail/inc/MethodInvoker.hpp | 31 ++++++++ .../rtl/detail/inc/forward_decls.h | 7 +- .../rtl/dispatch/lambda_function.h | 4 +- .../rtl/dispatch/lambda_method.h | 4 +- ReflectionTemplateLib/rtl/inc/Function.h | 13 +--- ReflectionTemplateLib/rtl/inc/Function.hpp | 24 +------ ReflectionTemplateLib/rtl/inc/Method.h | 12 +--- ReflectionTemplateLib/rtl/inc/Method.hpp | 25 +------ 12 files changed, 166 insertions(+), 115 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index ca19a74a..4e981360 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -20,58 +20,58 @@ namespace cxx namespace { - static const auto getMessage_functor = []() + static const rtl::function getMessage = []() { std::optional function = cxx::mirror().getFunction("getMessage"); if(!function) { - std::cerr << "[00] error: function 'getMessage' not found.\n"; + std::cerr << "[00] error: function 'getMessage' not found.\callerId"; std::abort(); } - return function->args_t().return_t(); + return function->getLambda().argsT().returnT(); }(); - static const auto sendMessage_functor = []() + static const rtl::function sendMessage = []() { - std::optional sendMessage = cxx::mirror().getFunction("sendMessage"); - if(!sendMessage) + std::optional function = cxx::mirror().getFunction("sendMessage"); + if(!function) { - std::cerr << "[01] error: function 'sendMessage' not found.\n"; + std::cerr << "[01] error: function 'sendMessage' not found.\callerId"; std::abort(); } - return sendMessage->args_t().return_t(); + return function->getLambda().argsT().returnT(); }(); - static const auto getMessageOnNode_functor = []() + static const rtl::method getMessageNode = []() { std::optional Node = cxx::mirror().getRecord("Node"); if (!Node) { - std::cerr << "[x] error: record 'Node' not found.\n"; + std::cerr << "[x] error: record 'Node' not found.\callerId"; std::abort(); } std::optional method = Node->getMethod("getMessage"); if (!method) { - std::cerr << "[02] error: method 'Node::getMessage' not found.\n"; + std::cerr << "[02] error: method 'Node::getMessage' not found.\callerId"; std::abort(); } - return method->args_t().return_t(); + return method->getLambda().argsT().returnT(); }(); - static const auto sendMessageOnNode_functor = []() + static const rtl::method sendMessageOnNode = []() { std::optional Node = cxx::mirror().getRecord("Node"); if (!Node) { - std::cerr << "[x] error: record 'Node' not found.\n"; + std::cerr << "[x] error: record 'Node' not found.\callerId"; std::abort(); } std::optional method = Node->getMethod("sendMessage"); if (!method) { - std::cerr << "[3] error: method 'Node::sendMessage' not found.\n"; + std::cerr << "[3] error: method 'Node::sendMessage' not found.\callerId"; std::abort(); } - return method->args_t().return_t(); + return method->getLambda().argsT().returnT(); }(); } @@ -84,10 +84,10 @@ namespace }; template - static bool test(const T& functor, int n) + static bool test(const T& lambda, int callerId) { - if (!functor.is_valid()) { - std::cerr << "[" << n << "] error: functor not valid, return-type or signature mismatch.\n"; + if (!lambda.is_valid()) { + std::cerr << "[" << callerId << "] error: functor not valid, return-type or signature mismatch.\callerId"; std::abort(); } return true; @@ -98,30 +98,30 @@ namespace void FunctionPointerCall::returnTypeNonVoid(benchmark::State& state) { static auto _=_new_line(); - static auto is_ok = test(getMessage_functor, 0); + static auto is_ok = test(getMessage, 0); for (auto _ : state) { - benchmark::DoNotOptimize((getMessage_functor.f_ptr())(bm::g_longStr)); + benchmark::DoNotOptimize((getMessage.f_ptr())(bm::g_longStr)); } } void MethodFnPointerCall::returnTypeNonVoid(benchmark::State& state) { static bm::Node nodeObj; - static auto is_ok = test(getMessageOnNode_functor, 1); + static auto is_ok = test(getMessageNode, 1); for (auto _ : state) { - benchmark::DoNotOptimize((nodeObj.*getMessageOnNode_functor.f_ptr())(bm::g_longStr)); + benchmark::DoNotOptimize((nodeObj.*getMessageNode.f_ptr())(bm::g_longStr)); } } void FunctionPointerCall::returnTypeVoid(benchmark::State& state) { static auto _ = _new_line(); - static auto is_ok = test(sendMessage_functor, 2); + static auto is_ok = test(sendMessage, 2); for (auto _ : state) { - (sendMessage_functor.f_ptr())(bm::g_longStr); + (sendMessage.f_ptr())(bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } @@ -129,12 +129,12 @@ void FunctionPointerCall::returnTypeVoid(benchmark::State& state) void MethodFnPointerCall::returnTypeVoid(benchmark::State& state) { static bm::Node nodeObj; - static auto is_ok = test(getMessageOnNode_functor, 2); + static auto is_ok = test(getMessageNode, 2); for (auto _ : state) { - if (sendMessageOnNode_functor.is_valid()) + if (sendMessageOnNode.is_valid()) { - (nodeObj.*sendMessageOnNode_functor.f_ptr())(bm::g_longStr); + (nodeObj.*sendMessageOnNode.f_ptr())(bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } @@ -145,30 +145,30 @@ void MethodFnPointerCall::returnTypeVoid(benchmark::State& state) void ReflectedCallKnownReturn::typeNonVoid(benchmark::State& state) { static auto _ = _new_line(); - static auto is_ok = test(getMessage_functor, 3); + static auto is_ok = test(getMessage, 3); for (auto _ : state) { - benchmark::DoNotOptimize(getMessage_functor(bm::g_longStr)); + benchmark::DoNotOptimize(getMessage(bm::g_longStr)); } } void ReflectedMethodCallKnownReturn::typeNonVoid(benchmark::State& state) { static bm::Node nodeObj; - static auto is_ok = test(getMessageOnNode_functor, 4); + static auto is_ok = test(getMessageNode, 4); for (auto _ : state) { - benchmark::DoNotOptimize(getMessageOnNode_functor(nodeObj, bm::g_longStr)); + benchmark::DoNotOptimize(getMessageNode(nodeObj, bm::g_longStr)); } } void ReflectedCallKnownReturn::typeVoid(benchmark::State& state) { static auto _ = _new_line(); - static auto is_ok = test(sendMessage_functor, 0); + static auto is_ok = test(sendMessage, 0); for (auto _ : state) { - sendMessage_functor(bm::g_longStr); + sendMessage(bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } @@ -176,10 +176,10 @@ void ReflectedCallKnownReturn::typeVoid(benchmark::State& state) void ReflectedMethodCallKnownReturn::typeVoid(benchmark::State& state) { static bm::Node nodeObj; - static auto is_ok = test(sendMessageOnNode_functor, 5); + static auto is_ok = test(sendMessageOnNode, 5); for (auto _ : state) { - sendMessageOnNode_functor(nodeObj, bm::g_longStr); + sendMessageOnNode(nodeObj, bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h index ae63d80a..b4063ce4 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h @@ -20,20 +20,38 @@ namespace rtl::detail template struct FunctionCaller { - //the function to be called. const Function* m_function; public: template - rtl::Return call(_args&&...) const; + rtl::Return call(_args&&...) const noexcept; template - constexpr rtl::Return operator()(_args&&...params) const - { - return call(std::forward<_args>(params)...); - } + constexpr rtl::Return operator()(_args&&...params) const noexcept; friend Function; }; } + + +namespace rtl::detail +{ + template<> + struct Hopper + { + const std::vector& m_functorIds; + + template + struct Build + { + const dispatch::lambda_function<_signature...>* m_lambda = nullptr; + + template + constexpr const function<_returnType(_signature...)> returnT() const; + }; + + template + const Build<_signature...> argsT() const; + }; +} diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index f5426d05..428356b8 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -20,7 +20,7 @@ namespace rtl::detail { template template - FORCE_INLINE Return FunctionCaller<_signature...>::call(_args&&...params) const + FORCE_INLINE Return FunctionCaller<_signature...>::call(_args&&...params) const noexcept { using Container = std::conditional_t...>, @@ -32,4 +32,39 @@ namespace rtl::detail } return { error::SignatureMismatch, RObject{} }; } + + + template + template + constexpr inline rtl::Return FunctionCaller<_signature...>::operator()(_args&&...params) const noexcept + { + return call(std::forward<_args>(params)...); + } +} + + +namespace rtl::detail +{ + template + const Hopper::Build<_signature...> Hopper::argsT() const + { + for (auto& functorId : m_functorIds) + { + if (functorId.m_lambda->is_signature<_signature...>()) [[likely]] { + return { functorId.get_lambda_function<_signature...>() }; + } + } + return Build<_signature...>(); + } + + + template + template + inline constexpr const function<_returnType(_signature...)> Hopper::Build<_signature...>::returnT() const + { + if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) { + return m_lambda->template get_hopper<_returnType>(); + } + return function<_returnType(_signature...)>(); + } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h index 4cbb83fe..8f9d40bd 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h @@ -74,4 +74,26 @@ namespace rtl::detail { friend Method; }; +} + + +namespace rtl::detail +{ + template + struct Hopper + { + const std::vector& m_functorIds; + + template + struct Build + { + const dispatch::lambda_method<_recordType, _signature...>* m_lambda = nullptr; + + template + constexpr const method<_returnType(_recordType::*)(_signature...)> returnT() const; + }; + + template + const Build<_signature...> argsT() const; + }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index 76a1c4e9..ab007d71 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -146,4 +146,35 @@ namespace rtl::detail return { error::SignatureMismatch , RObject{} }; } } +} + + +namespace rtl::detail +{ + template + template + const Hopper<_recordType>::Build<_signature...> Hopper<_recordType>::argsT() const + { + for (auto& functorId : m_functorIds) + { + if (functorId.m_lambda->is_member<_recordType>() && + functorId.m_lambda->is_signature<_signature...>()) [[likely]] + { + return { functorId.get_lambda_method<_recordType, _signature...>() }; + } + } + return Build<_signature...>(); + } + + + template + template + template + inline constexpr const method<_returnType(_recordType::*)(_signature...)> Hopper<_recordType>::Build<_signature...>::returnT() const + { + if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) { + return m_lambda->template get_hopper<_returnType>(); + } + return method<_returnType(_recordType::*)(_signature...)>(); + } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h index a755fb9c..70420b2f 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h +++ b/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h @@ -26,10 +26,10 @@ namespace rtl class CxxMirror; template - struct function_hop; + struct function; template - struct method_hop; + struct method; namespace detail { @@ -40,6 +40,9 @@ namespace rtl template class SetupMethod; + + template + struct Hopper; } namespace cache diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 77587425..98424128 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -17,7 +17,7 @@ namespace rtl { template - struct function_hop + struct function { using fptr_t = return_t(*)(signature_ts...); @@ -55,7 +55,7 @@ namespace rtl::dispatch struct lambda_function: public lambda { template - using hopper_t = function_hop; + using hopper_t = function; lambda_function(const functor& p_functor) noexcept :lambda(p_functor) diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index d8cec377..6d771717 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -18,7 +18,7 @@ namespace rtl { template - struct method_hop + struct method { using fptr_t = return_t (record_t::*)(signature_ts...); @@ -56,7 +56,7 @@ namespace rtl::dispatch struct lambda_method : public lambda { template - using hopper_t = method_hop; + using hopper_t = method; lambda_method(const functor& p_functor) noexcept :lambda(p_functor) diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 2371f9b0..807f69a6 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -89,19 +89,8 @@ namespace rtl { Function& operator=(Function&&) = default; Function& operator=(const Function&) = default; - template - struct HopBuilder - { - const dispatch::lambda_function<_signature...>* m_lambda = nullptr; - - template - constexpr const function_hop<_returnType(_signature...)> return_t() const; - }; - - template - const HopBuilder<_signature...> args_t() const; + detail::Hopper<> getLambda(); - //indicates if a functor associated with it takes zero arguments. bool hasSignature() const; template diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index 49650789..da8aec10 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -22,31 +22,13 @@ namespace rtl return detail::FunctionCaller<_signature...>{ this }; } - template - const Function::HopBuilder<_signature...> Function::args_t() const - { - for (auto& functorId : m_functorIds) - { - if (functorId.m_lambda->is_signature<_signature...>()) [[likely]] { - return { functorId.get_lambda_function<_signature...>() }; - } - } - return HopBuilder<_signature...>(); - } - - template - template - inline constexpr const function_hop<_returnType(_signature...)> Function::HopBuilder<_signature...>::return_t() const + inline detail::Hopper<> Function::getLambda() { - if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) { - return m_lambda->template get_hopper<_returnType>(); - } - return function_hop<_returnType(_signature...)>(); + return detail::Hopper<>{ m_functorIds }; } - -/* @method: hasSignature<...>() + /* @method: hasSignature<...>() @param: set of arguments, explicitly specified as template parameter. @return: bool, if the functor associated with this object is of certain signature or not. * a single 'Function' object can be associated with multiple overloads of same function. diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index 4e46f80b..a2762b40 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -56,18 +56,8 @@ namespace rtl { GETTER_BOOL(Const, (getQualifier() == detail::methodQ::Const)); - - template - struct HopBuilder - { - const dispatch::lambda_method<_recordType, _signature...>* m_lambda = nullptr; - - template - constexpr const method_hop<_returnType (_recordType::*)(_signature...)> return_t() const; - }; - template - const HopBuilder<_recordType, _signature...> args_t() const; + constexpr detail::Hopper<_recordType> getLambda() const; //indicates if a particular set of arguments accepted by the functor associated with it. template diff --git a/ReflectionTemplateLib/rtl/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp index fb88da15..614d0bf3 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.hpp +++ b/ReflectionTemplateLib/rtl/inc/Method.hpp @@ -30,28 +30,9 @@ namespace rtl template - const Method::HopBuilder<_recordType, _signature...> Method::args_t() const + inline constexpr detail::Hopper<_recordType> Method::getLambda() const { - for (auto& functorId : getFunctorIds()) - { - if (functorId.m_lambda->is_member<_recordType>() && - functorId.m_lambda->is_signature<_signature...>()) [[likely]] - { - return { functorId.get_lambda_method<_recordType, _signature...>() }; - } - } - return HopBuilder<_recordType, _signature...>(); - } - - - template - template - inline constexpr const method_hop<_returnType (_recordType::*)(_signature...)> Method::HopBuilder<_recordType, _signature...>::return_t() const - { - if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) { - return m_lambda->template get_hopper<_returnType>(); - } - return method_hop<_returnType (_recordType::*)(_signature...)>(); + return detail::Hopper<_recordType>{ getFunctorIds() }; } @@ -72,7 +53,7 @@ namespace rtl } -/* @method: hasSignature<...>() + /* @method: hasSignature<...>() @params: template params, <_arg0, ..._args> (expects at least one args- _args0) @return: bool * checks if the member-function functor associated with this 'Method', takes template specified arguments set or not. From c30f20cb57e049786b7b10ae0ea3762d4ac0a741 Mon Sep 17 00:00:00 2001 From: neeraj Date: Tue, 23 Sep 2025 21:58:08 +0530 Subject: [PATCH 30/58] fixed gcc 'template' error --- .../src/ReflectedCallKnownReturn.cpp | 48 +++++++++---------- .../src/ReflectedCallKnownReturn.h | 24 +++++----- .../src/ReflectedCallUnknownReturn.cpp | 8 ++-- .../src/ReflectedCallUnknownReturn.h | 4 +- RTLBenchmarkApp/src/StandardCall.cpp | 16 +++---- RTLBenchmarkApp/src/StandardCall.h | 16 +++---- RTLBenchmarkApp/src/main.cpp | 36 +++++++------- .../rtl/detail/inc/MethodInvoker.hpp | 2 +- ReflectionTemplateLib/rtl/inc/Function.h | 2 +- ReflectionTemplateLib/rtl/inc/Function.hpp | 2 +- ReflectionTemplateLib/rtl/inc/Method.h | 2 +- ReflectionTemplateLib/rtl/inc/Method.hpp | 2 +- 12 files changed, 81 insertions(+), 81 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 4e981360..f9fdf180 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -25,10 +25,10 @@ namespace std::optional function = cxx::mirror().getFunction("getMessage"); if(!function) { - std::cerr << "[00] error: function 'getMessage' not found.\callerId"; + std::cerr << "[00] error: function 'getMessage' not found."; std::abort(); } - return function->getLambda().argsT().returnT(); + return function->lambda().argsT().returnT(); }(); static const rtl::function sendMessage = []() @@ -36,42 +36,42 @@ namespace std::optional function = cxx::mirror().getFunction("sendMessage"); if(!function) { - std::cerr << "[01] error: function 'sendMessage' not found.\callerId"; + std::cerr << "[01] error: function 'sendMessage' not found."; std::abort(); } - return function->getLambda().argsT().returnT(); + return function->lambda().argsT().returnT(); }(); static const rtl::method getMessageNode = []() { std::optional Node = cxx::mirror().getRecord("Node"); if (!Node) { - std::cerr << "[x] error: record 'Node' not found.\callerId"; + std::cerr << "[x] error: record 'Node' not found"; std::abort(); } std::optional method = Node->getMethod("getMessage"); if (!method) { - std::cerr << "[02] error: method 'Node::getMessage' not found.\callerId"; + std::cerr << "[02] error: method 'Node::getMessage' not found."; std::abort(); } - return method->getLambda().argsT().returnT(); + return method->lambda().argsT().returnT(); }(); - static const rtl::method sendMessageOnNode = []() + static const rtl::method sendMessageNode = []() { std::optional Node = cxx::mirror().getRecord("Node"); if (!Node) { - std::cerr << "[x] error: record 'Node' not found.\callerId"; + std::cerr << "[x] error: record 'Node' not found."; std::abort(); } std::optional method = Node->getMethod("sendMessage"); if (!method) { - std::cerr << "[3] error: method 'Node::sendMessage' not found.\callerId"; + std::cerr << "[3] error: method 'Node::sendMessage' not found."; std::abort(); } - return method->getLambda().argsT().returnT(); + return method->lambda().argsT().returnT(); }(); } @@ -87,7 +87,7 @@ namespace static bool test(const T& lambda, int callerId) { if (!lambda.is_valid()) { - std::cerr << "[" << callerId << "] error: functor not valid, return-type or signature mismatch.\callerId"; + std::cerr << "[" << callerId << "] error: functor not valid, return-type or signature mismatch."; std::abort(); } return true; @@ -95,7 +95,7 @@ namespace } -void FunctionPointerCall::returnTypeNonVoid(benchmark::State& state) +void NativeFunctionPtr_call::returnNonVoid(benchmark::State& state) { static auto _=_new_line(); static auto is_ok = test(getMessage, 0); @@ -105,7 +105,7 @@ void FunctionPointerCall::returnTypeNonVoid(benchmark::State& state) } } -void MethodFnPointerCall::returnTypeNonVoid(benchmark::State& state) +void NativeFunctionPtr_callMethod::returnNonVoid(benchmark::State& state) { static bm::Node nodeObj; static auto is_ok = test(getMessageNode, 1); @@ -115,7 +115,7 @@ void MethodFnPointerCall::returnTypeNonVoid(benchmark::State& state) } } -void FunctionPointerCall::returnTypeVoid(benchmark::State& state) +void NativeFunctionPtr_call::returnVoid(benchmark::State& state) { static auto _ = _new_line(); static auto is_ok = test(sendMessage, 2); @@ -126,15 +126,15 @@ void FunctionPointerCall::returnTypeVoid(benchmark::State& state) } } -void MethodFnPointerCall::returnTypeVoid(benchmark::State& state) +void NativeFunctionPtr_callMethod::returnVoid(benchmark::State& state) { static bm::Node nodeObj; static auto is_ok = test(getMessageNode, 2); for (auto _ : state) { - if (sendMessageOnNode.is_valid()) + if (sendMessageNode.is_valid()) { - (nodeObj.*sendMessageOnNode.f_ptr())(bm::g_longStr); + (nodeObj.*sendMessageNode.f_ptr())(bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } @@ -142,7 +142,7 @@ void MethodFnPointerCall::returnTypeVoid(benchmark::State& state) -void ReflectedCallKnownReturn::typeNonVoid(benchmark::State& state) +void RtlFunction_call::returnNonVoid(benchmark::State &state) { static auto _ = _new_line(); static auto is_ok = test(getMessage, 3); @@ -152,7 +152,7 @@ void ReflectedCallKnownReturn::typeNonVoid(benchmark::State& state) } } -void ReflectedMethodCallKnownReturn::typeNonVoid(benchmark::State& state) +void RtlFunction_callMethod::returnNonVoid(benchmark::State& state) { static bm::Node nodeObj; static auto is_ok = test(getMessageNode, 4); @@ -162,7 +162,7 @@ void ReflectedMethodCallKnownReturn::typeNonVoid(benchmark::State& state) } } -void ReflectedCallKnownReturn::typeVoid(benchmark::State& state) +void RtlFunction_call::returnVoid(benchmark::State& state) { static auto _ = _new_line(); static auto is_ok = test(sendMessage, 0); @@ -173,13 +173,13 @@ void ReflectedCallKnownReturn::typeVoid(benchmark::State& state) } } -void ReflectedMethodCallKnownReturn::typeVoid(benchmark::State& state) +void RtlFunction_callMethod::returnVoid(benchmark::State& state) { static bm::Node nodeObj; - static auto is_ok = test(sendMessageOnNode, 5); + static auto is_ok = test(sendMessageNode, 5); for (auto _ : state) { - sendMessageOnNode(nodeObj, bm::g_longStr); + sendMessageNode(nodeObj, bm::g_longStr); benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } \ No newline at end of file diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h index a6a5a61d..6e369771 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.h @@ -2,33 +2,33 @@ #include -struct ReflectedCallKnownReturn +struct RtlFunction_call { - static void typeVoid(benchmark::State& state); + static void returnVoid(benchmark::State& state); - static void typeNonVoid(benchmark::State& state); + static void returnNonVoid(benchmark::State& state); }; -struct FunctionPointerCall +struct NativeFunctionPtr_call { - static void returnTypeVoid(benchmark::State& state); + static void returnVoid(benchmark::State& state); - static void returnTypeNonVoid(benchmark::State& state); + static void returnNonVoid(benchmark::State& state); }; -struct MethodFnPointerCall +struct NativeFunctionPtr_callMethod { - static void returnTypeVoid(benchmark::State& state); + static void returnVoid(benchmark::State& state); - static void returnTypeNonVoid(benchmark::State& state); + static void returnNonVoid(benchmark::State& state); }; -struct ReflectedMethodCallKnownReturn +struct RtlFunction_callMethod { - static void typeVoid(benchmark::State& state); + static void returnVoid(benchmark::State& state); - static void typeNonVoid(benchmark::State& state); + static void returnNonVoid(benchmark::State& state); }; \ No newline at end of file diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index 760b7734..ab150e50 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -127,7 +127,7 @@ namespace -void ReflectedCallUnknownReturn::typeVoid(benchmark::State& state) +void RtlFunction_call_ReturnUnknown::typeVoid(benchmark::State& state) { static auto __=_new_line(); static auto _ = _test0(); @@ -138,7 +138,7 @@ void ReflectedCallUnknownReturn::typeVoid(benchmark::State& state) } -void ReflectedCallUnknownReturn::typeNonVoid(benchmark::State& state) +void RtlFunction_call_ReturnUnknown::typeNonVoid(benchmark::State& state) { static auto __=_new_line(); static auto _ = _test2(); @@ -149,7 +149,7 @@ void ReflectedCallUnknownReturn::typeNonVoid(benchmark::State& state) } -void ReflectedMethodCallUnknownReturn::typeVoid(benchmark::State& state) +void RtlFunctionCall_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) { static auto _ = _test1(); for (auto _ : state) @@ -159,7 +159,7 @@ void ReflectedMethodCallUnknownReturn::typeVoid(benchmark::State& state) } -void ReflectedMethodCallUnknownReturn::typeNonVoid(benchmark::State& state) +void RtlFunctionCall_callMethod_ReturnUnknown::typeNonVoid(benchmark::State& state) { static auto _ = _test3(); for (auto _ : state) diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h index 9ceec026..03a2dfd1 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h @@ -2,7 +2,7 @@ #include -struct ReflectedCallUnknownReturn +struct RtlFunction_call_ReturnUnknown { static void typeVoid(benchmark::State& state); @@ -10,7 +10,7 @@ struct ReflectedCallUnknownReturn }; -struct ReflectedMethodCallUnknownReturn +struct RtlFunctionCall_callMethod_ReturnUnknown { static void typeVoid(benchmark::State& state); diff --git a/RTLBenchmarkApp/src/StandardCall.cpp b/RTLBenchmarkApp/src/StandardCall.cpp index d79c3d44..215a92d4 100644 --- a/RTLBenchmarkApp/src/StandardCall.cpp +++ b/RTLBenchmarkApp/src/StandardCall.cpp @@ -9,8 +9,8 @@ namespace { static auto _put_line = []() { - std::cout << "----------------------------------------" - "------------------------------------------------" << std::endl; + std::cout << "--------------------------------------------" + "----------------------------------------------------" << std::endl; return 0; }; @@ -39,7 +39,7 @@ namespace bm } -void NativeCall::returnTypeVoid(benchmark::State& state) +void NativeCall::returnVoid(benchmark::State& state) { for (auto _: state) { @@ -49,7 +49,7 @@ void NativeCall::returnTypeVoid(benchmark::State& state) } -void NativeCall::returnTypeNonVoid(benchmark::State& state) +void NativeCall::returnNonVoid(benchmark::State& state) { static auto _=_put_line(); for (auto _: state) @@ -59,7 +59,7 @@ void NativeCall::returnTypeNonVoid(benchmark::State& state) } -void StdFunctionCall::returnTypeVoid(benchmark::State& state) +void StdFunction_call::returnVoid(benchmark::State& state) { static auto _=_new_line(); for (auto _: state) @@ -70,7 +70,7 @@ void StdFunctionCall::returnTypeVoid(benchmark::State& state) } -void StdFunctionMethodCall::returnTypeVoid(benchmark::State& state) +void StdFunction_callMethod::returnVoid(benchmark::State& state) { static bm::Node nodeObj; for (auto _: state) @@ -81,7 +81,7 @@ void StdFunctionMethodCall::returnTypeVoid(benchmark::State& state) } -void StdFunctionCall::returnTypeNonVoid(benchmark::State& state) +void StdFunction_call::returnNonVoid(benchmark::State& state) { static auto _=_new_line(); for (auto _: state) @@ -91,7 +91,7 @@ void StdFunctionCall::returnTypeNonVoid(benchmark::State& state) } -void StdFunctionMethodCall::returnTypeNonVoid(benchmark::State& state) +void StdFunction_callMethod::returnNonVoid(benchmark::State& state) { static bm::Node nodeObj; for (auto _: state) diff --git a/RTLBenchmarkApp/src/StandardCall.h b/RTLBenchmarkApp/src/StandardCall.h index e6ca7b00..bbc77907 100644 --- a/RTLBenchmarkApp/src/StandardCall.h +++ b/RTLBenchmarkApp/src/StandardCall.h @@ -4,23 +4,23 @@ struct NativeCall { - static void returnTypeVoid(benchmark::State& state); + static void returnVoid(benchmark::State& state); - static void returnTypeNonVoid(benchmark::State& state); + static void returnNonVoid(benchmark::State& state); }; -struct StdFunctionCall +struct StdFunction_call { - static void returnTypeVoid(benchmark::State& state); + static void returnVoid(benchmark::State& state); - static void returnTypeNonVoid(benchmark::State& state); + static void returnNonVoid(benchmark::State& state); }; -struct StdFunctionMethodCall +struct StdFunction_callMethod { - static void returnTypeVoid(benchmark::State& state); + static void returnVoid(benchmark::State& state); - static void returnTypeNonVoid(benchmark::State& state); + static void returnNonVoid(benchmark::State& state); }; \ No newline at end of file diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index 44119ff6..bde3f594 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -6,33 +6,33 @@ #include "ReflectedCallKnownReturn.h" #include "ReflectedCallUnknownReturn.h" -BENCHMARK(NativeCall::returnTypeVoid); +BENCHMARK(NativeCall::returnVoid); -BENCHMARK(FunctionPointerCall::returnTypeVoid); -BENCHMARK(MethodFnPointerCall::returnTypeVoid); +BENCHMARK(NativeFunctionPtr_call::returnVoid); +BENCHMARK(NativeFunctionPtr_callMethod::returnVoid); -BENCHMARK(StdFunctionCall::returnTypeVoid); -BENCHMARK(StdFunctionMethodCall::returnTypeVoid); +BENCHMARK(StdFunction_call::returnVoid); +BENCHMARK(StdFunction_callMethod::returnVoid); -BENCHMARK(ReflectedCallKnownReturn::typeVoid); -BENCHMARK(ReflectedMethodCallKnownReturn::typeVoid); +BENCHMARK(RtlFunction_call::returnVoid); +BENCHMARK(RtlFunction_callMethod::returnVoid); -BENCHMARK(ReflectedCallUnknownReturn::typeVoid); -BENCHMARK(ReflectedMethodCallUnknownReturn::typeVoid); +BENCHMARK(RtlFunction_call_ReturnUnknown::typeVoid); +BENCHMARK(RtlFunctionCall_callMethod_ReturnUnknown::typeVoid); -BENCHMARK(NativeCall::returnTypeNonVoid); +BENCHMARK(NativeCall::returnNonVoid); -BENCHMARK(FunctionPointerCall::returnTypeNonVoid); -BENCHMARK(MethodFnPointerCall::returnTypeNonVoid); +BENCHMARK(NativeFunctionPtr_call::returnNonVoid); +BENCHMARK(NativeFunctionPtr_callMethod::returnNonVoid); -BENCHMARK(StdFunctionCall::returnTypeNonVoid); -BENCHMARK(StdFunctionMethodCall::returnTypeNonVoid); +BENCHMARK(StdFunction_call::returnNonVoid); +BENCHMARK(StdFunction_callMethod::returnNonVoid); -BENCHMARK(ReflectedCallKnownReturn::typeNonVoid); -BENCHMARK(ReflectedMethodCallKnownReturn::typeNonVoid); +BENCHMARK(RtlFunction_call::returnNonVoid); +BENCHMARK(RtlFunction_callMethod::returnNonVoid); -BENCHMARK(ReflectedCallUnknownReturn::typeNonVoid); -BENCHMARK(ReflectedMethodCallUnknownReturn::typeNonVoid); +BENCHMARK(RtlFunction_call_ReturnUnknown::typeNonVoid); +BENCHMARK(RtlFunctionCall_callMethod_ReturnUnknown::typeNonVoid); namespace bm { diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index ab007d71..f66e9a7d 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -153,7 +153,7 @@ namespace rtl::detail { template template - const Hopper<_recordType>::Build<_signature...> Hopper<_recordType>::argsT() const + const Hopper<_recordType>::template Build<_signature...> Hopper<_recordType>::argsT() const { for (auto& functorId : m_functorIds) { diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 807f69a6..38e46d0f 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -89,7 +89,7 @@ namespace rtl { Function& operator=(Function&&) = default; Function& operator=(const Function&) = default; - detail::Hopper<> getLambda(); + detail::Hopper<> lambda(); bool hasSignature() const; diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index da8aec10..e4b3f3e1 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -23,7 +23,7 @@ namespace rtl } - inline detail::Hopper<> Function::getLambda() + inline detail::Hopper<> Function::lambda() { return detail::Hopper<>{ m_functorIds }; } diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index a2762b40..18cf1ea3 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -57,7 +57,7 @@ namespace rtl { GETTER_BOOL(Const, (getQualifier() == detail::methodQ::Const)); template - constexpr detail::Hopper<_recordType> getLambda() const; + constexpr detail::Hopper<_recordType> lambda() const; //indicates if a particular set of arguments accepted by the functor associated with it. template diff --git a/ReflectionTemplateLib/rtl/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp index 614d0bf3..91f7c56f 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.hpp +++ b/ReflectionTemplateLib/rtl/inc/Method.hpp @@ -30,7 +30,7 @@ namespace rtl template - inline constexpr detail::Hopper<_recordType> Method::getLambda() const + inline constexpr detail::Hopper<_recordType> Method::lambda() const { return detail::Hopper<_recordType>{ getFunctorIds() }; } From e82728be3343f58e665b532099d3d7d6765b866d Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Tue, 23 Sep 2025 23:17:06 +0530 Subject: [PATCH 31/58] err fix: msvc, removed nested/dependent templates --- .../rtl/detail/inc/FunctionCaller.h | 23 ++++++++++--------- .../rtl/detail/inc/FunctionCaller.hpp | 8 ++++--- .../rtl/detail/inc/MethodInvoker.h | 20 ++++++++-------- .../rtl/detail/inc/MethodInvoker.hpp | 11 +++++---- 4 files changed, 33 insertions(+), 29 deletions(-) diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h index b4063ce4..93b5bfbc 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h @@ -37,21 +37,22 @@ namespace rtl::detail namespace rtl::detail { - template<> - struct Hopper + template + struct HopFunction { - const std::vector& m_functorIds; + const dispatch::lambda_function<_signature...>* m_lambda = nullptr; - template - struct Build - { - const dispatch::lambda_function<_signature...>* m_lambda = nullptr; + template + constexpr const function<_returnType(_signature...)> returnT() const; + }; - template - constexpr const function<_returnType(_signature...)> returnT() const; - }; + + template<> + struct Hopper<> + { + const std::vector& m_functorIds; template - const Build<_signature...> argsT() const; + const HopFunction<_signature...> argsT() const; }; } diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index 428356b8..3d0079fd 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -46,7 +46,7 @@ namespace rtl::detail namespace rtl::detail { template - const Hopper::Build<_signature...> Hopper::argsT() const + const HopFunction<_signature...> Hopper<>::argsT() const { for (auto& functorId : m_functorIds) { @@ -54,13 +54,15 @@ namespace rtl::detail return { functorId.get_lambda_function<_signature...>() }; } } - return Build<_signature...>(); + return HopFunction<_signature...>(); } template template - inline constexpr const function<_returnType(_signature...)> Hopper::Build<_signature...>::returnT() const + inline constexpr + const function<_returnType(_signature...)> + HopFunction<_signature...>::returnT() const { if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) { return m_lambda->template get_hopper<_returnType>(); diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h index 8f9d40bd..1c370da4 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h @@ -79,21 +79,21 @@ namespace rtl::detail { namespace rtl::detail { + template + struct HopMethod + { + const dispatch::lambda_method<_recordType, _signature...>* m_lambda = nullptr; + + template + constexpr const method<_returnType(_recordType::*)(_signature...)> returnT() const; + }; + template struct Hopper { const std::vector& m_functorIds; template - struct Build - { - const dispatch::lambda_method<_recordType, _signature...>* m_lambda = nullptr; - - template - constexpr const method<_returnType(_recordType::*)(_signature...)> returnT() const; - }; - - template - const Build<_signature...> argsT() const; + constexpr HopMethod<_recordType, _signature...> argsT() const; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index f66e9a7d..b83c1e97 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -153,7 +153,7 @@ namespace rtl::detail { template template - const Hopper<_recordType>::template Build<_signature...> Hopper<_recordType>::argsT() const + inline constexpr HopMethod<_recordType, _signature...> Hopper<_recordType>::argsT() const { for (auto& functorId : m_functorIds) { @@ -163,14 +163,15 @@ namespace rtl::detail return { functorId.get_lambda_method<_recordType, _signature...>() }; } } - return Build<_signature...>(); + return HopMethod<_recordType, _signature...>(); } - template - template + template template - inline constexpr const method<_returnType(_recordType::*)(_signature...)> Hopper<_recordType>::Build<_signature...>::returnT() const + inline constexpr + const method<_returnType(_recordType::*)(_signature...)> + HopMethod<_recordType, _signature...>::returnT() const { if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) { return m_lambda->template get_hopper<_returnType>(); From 3a6ab51ae62d05f173d68c3c627c9319336e45ca Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Wed, 24 Sep 2025 01:16:52 +0530 Subject: [PATCH 32/58] specalized cache/method_ptr for const-member-functors. --- .../rtl/builder/SetupMethod.hpp | 12 ++++---- .../rtl/cache/cache_const_method_ptr.h | 30 ++++++++++--------- .../rtl/cache/cache_function_ptr.h | 4 +-- .../rtl/cache/cache_method_ptr.h | 12 ++++---- .../rtl/dispatch/const_method_ptr.h | 7 +++-- 5 files changed, 35 insertions(+), 30 deletions(-) diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 0fdead0c..8d8f13a6 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -34,8 +34,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - // bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor().f_ptr()); - // assert(isFunctorGood && "new type-id-system not working."); + //bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor().f_ptr()); + //assert(isFunctorGood && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -57,8 +57,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - // bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor<_returnType>().f_ptr()); - // assert(isFunctorGood && "new type-id-system not working."); + //bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor<_returnType>().f_ptr()); + //assert(isFunctorGood && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -238,7 +238,7 @@ namespace rtl::detail const auto& updateIndex = [&](std::size_t pIndex)-> void { auto& lambdaCache = cache::lambda_method<_recordType, _signature...>::instance(); - auto& functorCache = cache::const_method_ptr<_recordType, _returnType, _signature...>::instance(); + auto& functorCache = cache::method_ptr::instance(); auto& functor = functorCache.push(pFunctor, pIndex); auto& lambda = lambdaCache.push(functor); @@ -248,7 +248,7 @@ namespace rtl::detail const auto& getIndex = [&]()-> std::size_t { - auto& functorCache = cache::const_method_ptr<_recordType, _returnType, _signature...>::instance(); + auto& functorCache = cache::method_ptr::instance(); auto [functor, lambdaIndex] = functorCache.find(pFunctor); if (lambdaIndex != rtl::index_none) { diff --git a/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h index e4a8826b..3cc9783d 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h @@ -15,26 +15,28 @@ #include "const_method_ptr.h" -namespace rtl::cache +namespace rtl::cache { template - struct const_method_ptr + struct method_ptr { - using functor_t = dispatch::const_method_ptr; + using method_t = dispatch::method_ptr; - static const const_method_ptr& instance() + using functor_t = return_t(record_t::*)(signature_ts...) const; + + static const method_ptr& instance() { - static const const_method_ptr instance_; + static const method_ptr instance_; return instance_; } - const dispatch::functor& push(return_t(record_t::* fptr)(signature_ts...) const, std::size_t lambda_index) const + const dispatch::functor& push(functor_t fptr, std::size_t lambda_index) const { - m_cache.emplace_back(std::make_pair(fptr, lambda_index)); + m_cache.emplace_back(std::make_pair(method_t(fptr), lambda_index)); return m_cache.back().first; } - std::pair find(return_t(record_t::* fptr)(signature_ts...) const) const + std::pair find(functor_t fptr) const { for (auto& itr : m_cache) { @@ -46,16 +48,16 @@ namespace rtl::cache return { nullptr, rtl::index_none }; } - const_method_ptr(const_method_ptr&&) = delete; - const_method_ptr(const const_method_ptr&) = delete; - const_method_ptr& operator=(const_method_ptr&&) = delete; - const_method_ptr& operator=(const const_method_ptr&) = delete; + method_ptr(method_ptr&&) = delete; + method_ptr(const method_ptr&) = delete; + method_ptr& operator=(method_ptr&&) = delete; + method_ptr& operator=(const method_ptr&) = delete; private: // No reallocation occurs; original objects stay intact - mutable std::list> m_cache; + mutable std::list> m_cache; - const_method_ptr() = default; + method_ptr() = default; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h index 8167b8fe..34c40f4b 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h @@ -20,7 +20,7 @@ namespace rtl::cache template struct function_ptr { - using functor_t = dispatch::function_ptr; + using function_t = dispatch::function_ptr; static const function_ptr& instance() { @@ -54,7 +54,7 @@ namespace rtl::cache private: // No reallocation occurs; original objects stay intact - mutable std::list> m_cache; + mutable std::list> m_cache; function_ptr() = default; }; diff --git a/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h index a607f1e2..59ce1144 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h @@ -20,7 +20,9 @@ namespace rtl::cache template struct method_ptr { - using functor_t = dispatch::method_ptr; + using method_t = dispatch::method_ptr; + + using functor_t = return_t(record_t::*)(signature_ts...); static const method_ptr& instance() { @@ -28,13 +30,13 @@ namespace rtl::cache return instance_; } - const dispatch::functor& push(return_t(record_t::* fptr)(signature_ts...), std::size_t lambda_index) const + const dispatch::functor& push(functor_t fptr, std::size_t lambda_index) const { - m_cache.emplace_back(std::make_pair(fptr, lambda_index)); + m_cache.emplace_back(std::make_pair(method_t(fptr), lambda_index)); return m_cache.back().first; } - std::pair find(return_t(record_t::* fptr)(signature_ts...)) const + std::pair find(functor_t fptr) const { for (auto& itr : m_cache) { @@ -54,7 +56,7 @@ namespace rtl::cache private: // No reallocation occurs; original objects stay intact - mutable std::list> m_cache; + mutable std::list> m_cache; method_ptr() = default; }; diff --git a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h index e555d72f..0efabe53 100644 --- a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h @@ -18,11 +18,11 @@ namespace rtl::dispatch { template - struct const_method_ptr : public functor + struct method_ptr : public functor { using functor_t = return_t(record_t::*)(signature_ts...) const; - constexpr functor_t get() const + [[nodiscard]] constexpr auto f_ptr() const { return m_functor; } @@ -32,8 +32,9 @@ namespace rtl::dispatch return (fptr == m_functor); } - const_method_ptr(functor_t fptr) :m_functor(fptr) + method_ptr(functor_t fptr) :m_functor(fptr) { + m_recordId = detail::TypeId>::get(); m_returnId = detail::TypeId>::get(); m_signatureId = detail::TypeId...>>::get(); } From e1901e1217bb4d6de4c84c3a0a98c67e58241a68 Mon Sep 17 00:00:00 2001 From: neeraj Date: Wed, 24 Sep 2025 08:42:10 +0530 Subject: [PATCH 33/58] minor refactor. --- RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp | 4 ++-- RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h | 2 +- RTLBenchmarkApp/src/main.cpp | 4 ++-- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index ab150e50..119e5eff 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -149,7 +149,7 @@ void RtlFunction_call_ReturnUnknown::typeNonVoid(benchmark::State& state) } -void RtlFunctionCall_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) +void RtlFunction_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) { static auto _ = _test1(); for (auto _ : state) @@ -159,7 +159,7 @@ void RtlFunctionCall_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) } -void RtlFunctionCall_callMethod_ReturnUnknown::typeNonVoid(benchmark::State& state) +void RtlFunction_callMethod_ReturnUnknown::typeNonVoid(benchmark::State& state) { static auto _ = _test3(); for (auto _ : state) diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h index 03a2dfd1..cc986820 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h @@ -10,7 +10,7 @@ struct RtlFunction_call_ReturnUnknown }; -struct RtlFunctionCall_callMethod_ReturnUnknown +struct RtlFunction_callMethod_ReturnUnknown { static void typeVoid(benchmark::State& state); diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index bde3f594..1c2c145d 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -18,7 +18,7 @@ BENCHMARK(RtlFunction_call::returnVoid); BENCHMARK(RtlFunction_callMethod::returnVoid); BENCHMARK(RtlFunction_call_ReturnUnknown::typeVoid); -BENCHMARK(RtlFunctionCall_callMethod_ReturnUnknown::typeVoid); +BENCHMARK(RtlFunction_callMethod_ReturnUnknown::typeVoid); BENCHMARK(NativeCall::returnNonVoid); @@ -32,7 +32,7 @@ BENCHMARK(RtlFunction_call::returnNonVoid); BENCHMARK(RtlFunction_callMethod::returnNonVoid); BENCHMARK(RtlFunction_call_ReturnUnknown::typeNonVoid); -BENCHMARK(RtlFunctionCall_callMethod_ReturnUnknown::typeNonVoid); +BENCHMARK(RtlFunction_callMethod_ReturnUnknown::typeNonVoid); namespace bm { From 046ad80c1ead8964f5d710db4b7550766cebe181 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Wed, 24 Sep 2025 14:41:21 +0530 Subject: [PATCH 34/58] enabled const-methods access from cache, tests:passing. --- .../src/ReflectedCallKnownReturn.cpp | 9 +-- .../rtl/builder/SetupFunction.hpp | 8 +-- .../rtl/builder/SetupMethod.hpp | 16 +++--- .../rtl/detail/inc/FunctionCaller.h | 4 +- .../rtl/detail/inc/FunctionCaller.hpp | 4 +- .../rtl/detail/inc/FunctorId.h | 4 +- .../rtl/dispatch/const_method_ptr.h | 7 ++- .../rtl/dispatch/function_ptr.h | 7 ++- ReflectionTemplateLib/rtl/dispatch/functor.h | 4 ++ ReflectionTemplateLib/rtl/dispatch/lambda.h | 6 +- .../rtl/dispatch/lambda_function.h | 2 +- .../rtl/dispatch/lambda_method.h | 55 ++++++++++++++++++- .../rtl/dispatch/method_ptr.h | 11 +++- ReflectionTemplateLib/rtl/inc/Function.h | 4 +- ReflectionTemplateLib/rtl/inc/Function.hpp | 4 +- 15 files changed, 104 insertions(+), 41 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index f9fdf180..7dd43790 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -86,7 +86,7 @@ namespace template static bool test(const T& lambda, int callerId) { - if (!lambda.is_valid()) { + if (!lambda) { std::cerr << "[" << callerId << "] error: functor not valid, return-type or signature mismatch."; std::abort(); } @@ -132,11 +132,8 @@ void NativeFunctionPtr_callMethod::returnVoid(benchmark::State& state) static auto is_ok = test(getMessageNode, 2); for (auto _ : state) { - if (sendMessageNode.is_valid()) - { - (nodeObj.*sendMessageNode.f_ptr())(bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done->c_str()); - } + (nodeObj.*sendMessageNode.f_ptr())(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index 1677e692..a9e460cd 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -30,8 +30,8 @@ namespace rtl { return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { - // bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_function<_signature...>()->template get_functor().f_ptr()); - // assert(isFunctorGood && "new type-id-system not working."); + decltype(pFunctor) functor = pFunctorId.get_lambda_function<_signature...>()->template get_hopper().f_ptr(); + assert((functor == pFunctor) && "new type-id-system not working."); pFunctor(std::forward<_signature>(params)...); return { error::None, RObject{} }; @@ -48,8 +48,8 @@ namespace rtl this is stored in _derivedType's (FunctorContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, _signature&&...params)-> Return { - // bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_function<_signature...>()->template get_functor<_returnType>().f_ptr()); - // assert(isFunctorGood && "new type-id-system not working."); + decltype(pFunctor) functor = pFunctorId.get_lambda_function<_signature...>()->template get_hopper<_returnType>().f_ptr(); + assert((functor == pFunctor) && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 8d8f13a6..793ff705 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -34,8 +34,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - //bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor().f_ptr()); - //assert(isFunctorGood && "new type-id-system not working."); + auto functor = pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_hopper().f_ptr(); + assert((functor == pFunctor) && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -57,8 +57,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - //bool isFunctorGood = (pFunctor == pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_functor<_returnType>().f_ptr()); - //assert(isFunctorGood && "new type-id-system not working."); + decltype(pFunctor) functor = pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_hopper<_returnType>().f_ptr(); + assert((functor == pFunctor) && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -101,8 +101,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - // bool isLambdaGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->get_functor().get_lambda()); - // assert(isLambdaGood && "new type-id-system not working."); + decltype(pFunctor) functor = pFunctorId.get_lambda_method()->template get_hopper().f_ptr(); + assert(pFunctor == functor && "new type-id-system not working."); const _recordType& target = pTargetObj.view<_recordType>()->get(); (target.*pFunctor)(std::forward<_signature>(params)...); @@ -120,8 +120,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - // bool isLambdaGood = (pFunctorId.m_lambda == pFunctorId.m_lambda->get_functor().get_lambda()); - // assert(isLambdaGood && "new type-id-system not working."); + decltype(pFunctor) functor = pFunctorId.get_lambda_method()->template get_hopper<_returnType>().f_ptr(); + assert(pFunctor == functor && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); //'target' is const and 'pFunctor' is const-member-function. diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h index 93b5bfbc..953cb600 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h @@ -53,6 +53,6 @@ namespace rtl::detail const std::vector& m_functorIds; template - const HopFunction<_signature...> argsT() const; + constexpr const HopFunction<_signature...> argsT() const; }; -} +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index 3d0079fd..c0503298 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -46,7 +46,7 @@ namespace rtl::detail namespace rtl::detail { template - const HopFunction<_signature...> Hopper<>::argsT() const + inline constexpr const HopFunction<_signature...> Hopper<>::argsT() const { for (auto& functorId : m_functorIds) { @@ -64,7 +64,7 @@ namespace rtl::detail const function<_returnType(_signature...)> HopFunction<_signature...>::returnT() const { - if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) { + if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) [[likely]] { return m_lambda->template get_hopper<_returnType>(); } return function<_returnType(_signature...)>(); diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index bd919b1a..0f26862f 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -81,13 +81,13 @@ namespace rtl::detail } template - const dispatch::lambda_function<_signature...>* get_lambda_function() const + constexpr const dispatch::lambda_function<_signature...>* get_lambda_function() const { return m_lambda->to_function<_signature...>(); } template - const dispatch::lambda_method<_recordType, _signature...>* get_lambda_method() const + constexpr const dispatch::lambda_method<_recordType, _signature...>* get_lambda_method() const { return m_lambda->to_method<_recordType, _signature...>(); } diff --git a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h index 0efabe53..d229e29d 100644 --- a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h @@ -34,9 +34,14 @@ namespace rtl::dispatch method_ptr(functor_t fptr) :m_functor(fptr) { - m_recordId = detail::TypeId>::get(); + m_qualifier = detail::methodQ::Const; + m_recordId = detail::TypeId::get(); m_returnId = detail::TypeId>::get(); m_signatureId = detail::TypeId...>>::get(); + + m_returnStr = detail::TypeId::toString(); + m_recordStr = detail::TypeId::toString(); + m_signatureStr = detail::TypeId::toString(); } private: diff --git a/ReflectionTemplateLib/rtl/dispatch/function_ptr.h b/ReflectionTemplateLib/rtl/dispatch/function_ptr.h index 7de9df89..0ce1b59c 100644 --- a/ReflectionTemplateLib/rtl/dispatch/function_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/function_ptr.h @@ -32,12 +32,15 @@ namespace rtl::dispatch function_ptr(functor_t fptr) :m_functor(fptr) { - m_returnId = detail::TypeId>::get(); + m_returnId = detail::TypeId::get(); m_signatureId = detail::TypeId...>>::get(); + + m_returnStr = detail::TypeId::toString(); + m_signatureStr = detail::TypeId::toString(); } private: - const functor_t m_functor; + functor_t m_functor; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index 06a6a9ce..c071582d 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -23,6 +23,10 @@ namespace rtl::dispatch std::size_t m_returnId = detail::TypeId<>::None; std::size_t m_signatureId = detail::TypeId<>::None; + std::string m_recordStr; + std::string m_returnStr; + std::string m_signatureStr; + std::vector m_argumentsId = {}; detail::methodQ m_qualifier = detail::methodQ::None; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index 36a3ef0c..c3f4b1d1 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -51,7 +51,7 @@ namespace rtl::dispatch template constexpr bool is_returning() const { - return (m_functor.m_returnId == detail::TypeId>::get()); + return (m_functor.m_returnId == detail::TypeId::get()); } template @@ -63,8 +63,8 @@ namespace rtl::dispatch template constexpr bool is_member() const { - return (m_functor.m_recordId == detail::TypeId>::get() || - m_functor.m_recordId == detail::TypeId>::get()); + return (m_functor.m_recordId == detail::TypeId::get() || + m_functor.m_recordId == detail::TypeId::get()); } friend detail::FunctorId; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 98424128..7b87a3fb 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -27,7 +27,7 @@ namespace rtl return m_functor; } - constexpr auto is_valid() const { + constexpr operator bool() const { return (m_functor != nullptr); } diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index 6d771717..766ca007 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -14,7 +14,6 @@ #include "lambda.h" #include "method_ptr.h" - namespace rtl { template @@ -28,7 +27,7 @@ namespace rtl return m_functor; } - constexpr auto is_valid() const { + constexpr operator bool() const { return (m_functor != nullptr); } @@ -50,6 +49,41 @@ namespace rtl } +namespace rtl +{ + template + struct method + { + using fptr_t = return_t(record_t::*)(signature_ts...) const; + + const fptr_t m_functor = nullptr; + + constexpr auto f_ptr() const { + return m_functor; + } + + constexpr operator bool() const { + return (m_functor != nullptr); + } + + template + [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept(noexcept_v) + { + static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + return (target.*m_functor)(std::forward(params)...); + } + + private: + + template + static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; + + template + static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); + }; +} + + namespace rtl::dispatch { template @@ -58,11 +92,14 @@ namespace rtl::dispatch template using hopper_t = method; + template + using hopper_ct = method; + lambda_method(const functor& p_functor) noexcept :lambda(p_functor) { } - template + template requires (std::is_const_v == false) constexpr const hopper_t get_hopper() const { if (m_functor.m_returnId == detail::TypeId::get()) @@ -73,5 +110,17 @@ namespace rtl::dispatch } return hopper_t(); } + + template requires (std::is_const_v == true) + constexpr const hopper_ct get_hopper() const + { + if (m_functor.m_returnId == detail::TypeId::get()) + { + return hopper_ct { + static_cast&>(m_functor).f_ptr() + }; + } + return hopper_ct(); + } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h index 60ae79fb..479e3ba5 100644 --- a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/method_ptr.h @@ -34,13 +34,18 @@ namespace rtl::dispatch method_ptr(functor_t fptr) :m_functor(fptr) { - m_recordId = detail::TypeId>::get(); - m_returnId = detail::TypeId>::get(); + m_qualifier = detail::methodQ::NonConst; + m_recordId = detail::TypeId::get(); + m_returnId = detail::TypeId::get(); m_signatureId = detail::TypeId...>>::get(); + + m_returnStr = detail::TypeId::toString(); + m_recordStr = detail::TypeId::toString(); + m_signatureStr = detail::TypeId::toString(); } private: - const functor_t m_functor; + functor_t m_functor; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 38e46d0f..3bdab774 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -89,7 +89,7 @@ namespace rtl { Function& operator=(Function&&) = default; Function& operator=(const Function&) = default; - detail::Hopper<> lambda(); + constexpr detail::Hopper<> lambda() const; bool hasSignature() const; @@ -100,7 +100,7 @@ namespace rtl { Return operator()(_args&&...params) const noexcept; template - const detail::FunctionCaller<_signature...> bind() const noexcept; + constexpr const detail::FunctionCaller<_signature...> bind() const noexcept; friend detail::CxxReflection; friend detail::ReflectionBuilder; diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index e4b3f3e1..a102d50b 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -17,13 +17,13 @@ namespace rtl { template - inline const detail::FunctionCaller<_signature...> Function::bind() const noexcept + inline constexpr const detail::FunctionCaller<_signature...> Function::bind() const noexcept { return detail::FunctionCaller<_signature...>{ this }; } - inline detail::Hopper<> Function::lambda() + inline constexpr detail::Hopper<> Function::lambda() const { return detail::Hopper<>{ m_functorIds }; } From 5099da50be54e2ef7c26f43299f959036317cc30 Mon Sep 17 00:00:00 2001 From: neeraj Date: Wed, 24 Sep 2025 15:29:54 +0530 Subject: [PATCH 35/58] minor refactor. --- ReflectionTemplateLib/rtl/CMakeLists.txt | 1 + ReflectionTemplateLib/rtl/builder/SetupConstructor.h | 2 +- ReflectionTemplateLib/rtl/builder/SetupFunction.h | 2 +- ReflectionTemplateLib/rtl/builder/SetupMethod.h | 2 +- ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt | 1 - ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h | 2 +- ReflectionTemplateLib/rtl/detail/inc/FunctorId.h | 2 +- ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h | 2 +- ReflectionTemplateLib/rtl/detail/inc/RObjectId.h | 2 +- ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h | 2 +- ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h | 2 +- ReflectionTemplateLib/rtl/dispatch/functor.h | 2 +- ReflectionTemplateLib/rtl/inc/RObject.h | 2 +- .../rtl/{detail/inc/forward_decls.h => rtl_forward_decls.h} | 0 ReflectionTemplateLib/rtl/rtl_traits.h | 2 +- 15 files changed, 13 insertions(+), 13 deletions(-) rename ReflectionTemplateLib/rtl/{detail/inc/forward_decls.h => rtl_forward_decls.h} (100%) diff --git a/ReflectionTemplateLib/rtl/CMakeLists.txt b/ReflectionTemplateLib/rtl/CMakeLists.txt index 0f97298d..dd7b3895 100644 --- a/ReflectionTemplateLib/rtl/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/CMakeLists.txt @@ -3,6 +3,7 @@ # Top-level headers in rtl/ (absolute paths) set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/rtl.h" + "${CMAKE_CURRENT_SOURCE_DIR}/rtl_forward_decls.h" "${CMAKE_CURRENT_SOURCE_DIR}/rtl_constants.h" "${CMAKE_CURRENT_SOURCE_DIR}/rtl_errors.h" "${CMAKE_CURRENT_SOURCE_DIR}/rtl_traits.h" diff --git a/ReflectionTemplateLib/rtl/builder/SetupConstructor.h b/ReflectionTemplateLib/rtl/builder/SetupConstructor.h index 6dfc38b2..ee41ec5b 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupConstructor.h +++ b/ReflectionTemplateLib/rtl/builder/SetupConstructor.h @@ -13,7 +13,7 @@ #include "FunctorId.h" -#include "forward_decls.h" +#include "rtl_forward_decls.h" namespace rtl { diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.h b/ReflectionTemplateLib/rtl/builder/SetupFunction.h index bdcad635..33dee711 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.h +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.h @@ -11,7 +11,7 @@ #pragma once -#include "forward_decls.h" +#include "rtl_forward_decls.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.h b/ReflectionTemplateLib/rtl/builder/SetupMethod.h index 768bcff4..7e2dc220 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.h +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.h @@ -11,7 +11,7 @@ #pragma once -#include "forward_decls.h" +#include "rtl_forward_decls.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt b/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt index ff6e9609..a4020ede 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt @@ -4,7 +4,6 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/ConversionUtils.h" "${CMAKE_CURRENT_SOURCE_DIR}/CxxReflection.h" - "${CMAKE_CURRENT_SOURCE_DIR}/forward_decls.h" "${CMAKE_CURRENT_SOURCE_DIR}/FunctorId.h" "${CMAKE_CURRENT_SOURCE_DIR}/ReflectCast.h" "${CMAKE_CURRENT_SOURCE_DIR}/ReflectCast.hpp" diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h index 953cb600..957c8c00 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h @@ -11,7 +11,7 @@ #pragma once -#include "forward_decls.h" +#include "rtl_forward_decls.h" #include "RObject.h" diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index 0f26862f..5db78d47 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -13,7 +13,7 @@ #include "rtl_typeid.h" #include "rtl_constants.h" -#include "forward_decls.h" +#include "rtl_forward_decls.h" #include "lambda_method.h" #include "lambda_function.h" diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h index 1c370da4..38ba7f74 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h @@ -11,7 +11,7 @@ #pragma once -#include "forward_decls.h" +#include "rtl_forward_decls.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h b/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h index 403e9b96..cab52049 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h @@ -16,7 +16,7 @@ #include #include "ReflectCast.h" -#include "forward_decls.h" +#include "rtl_forward_decls.h" #include "FunctorId.h" namespace rtl::detail diff --git a/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h b/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h index 1e3fc638..104d1142 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h +++ b/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h @@ -16,7 +16,7 @@ #include #include "rtl_traits.h" -#include "forward_decls.h" +#include "rtl_forward_decls.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h index d229e29d..002c7794 100644 --- a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h +++ b/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h @@ -36,7 +36,7 @@ namespace rtl::dispatch { m_qualifier = detail::methodQ::Const; m_recordId = detail::TypeId::get(); - m_returnId = detail::TypeId>::get(); + m_returnId = detail::TypeId::get(); m_signatureId = detail::TypeId...>>::get(); m_returnStr = detail::TypeId::toString(); diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index c071582d..06ee12a6 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -13,7 +13,7 @@ #include "rtl_typeid.h" #include "rtl_constants.h" -#include "forward_decls.h" +#include "rtl_forward_decls.h" namespace rtl::dispatch { diff --git a/ReflectionTemplateLib/rtl/inc/RObject.h b/ReflectionTemplateLib/rtl/inc/RObject.h index 3705c3a7..4e89d6f7 100644 --- a/ReflectionTemplateLib/rtl/inc/RObject.h +++ b/ReflectionTemplateLib/rtl/inc/RObject.h @@ -18,7 +18,7 @@ #include "rtl_traits.h" #include "rtl_errors.h" -#include "forward_decls.h" +#include "rtl_forward_decls.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/detail/inc/forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h similarity index 100% rename from ReflectionTemplateLib/rtl/detail/inc/forward_decls.h rename to ReflectionTemplateLib/rtl/rtl_forward_decls.h diff --git a/ReflectionTemplateLib/rtl/rtl_traits.h b/ReflectionTemplateLib/rtl/rtl_traits.h index 84f4d631..0bef3cda 100644 --- a/ReflectionTemplateLib/rtl/rtl_traits.h +++ b/ReflectionTemplateLib/rtl/rtl_traits.h @@ -19,7 +19,7 @@ #include "rtl_typeid.h" #include "rtl_constants.h" -#include "forward_decls.h" +#include "rtl_forward_decls.h" namespace rtl { From 24f9fa2a181f802cd87900cc03c45b881c022a73 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Wed, 24 Sep 2025 21:17:30 +0530 Subject: [PATCH 36/58] interface refined. wip. --- .../rtl/builder/SetupFunction.hpp | 22 ++++++-- .../rtl/builder/SetupMethod.hpp | 50 +++++++++++++++---- .../rtl/detail/inc/FunctionCaller.hpp | 11 ++-- .../rtl/detail/inc/FunctorId.h | 10 ++-- .../rtl/detail/inc/MethodInvoker.hpp | 15 +++--- ReflectionTemplateLib/rtl/dispatch/functor.h | 4 +- ReflectionTemplateLib/rtl/dispatch/lambda.h | 20 +++++--- .../rtl/dispatch/lambda_function.h | 11 ++-- .../rtl/dispatch/lambda_method.h | 14 +++--- ReflectionTemplateLib/rtl/rtl_forward_decls.h | 2 +- 10 files changed, 108 insertions(+), 51 deletions(-) diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index a9e460cd..2af99d2a 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -30,8 +30,14 @@ namespace rtl { return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return { - decltype(pFunctor) functor = pFunctorId.get_lambda_function<_signature...>()->template get_hopper().f_ptr(); - assert((functor == pFunctor) && "new type-id-system not working."); + auto retId = TypeId::get(); + auto argsId = TypeId...>>::get(); + + decltype(pFunctor) functor = pFunctorId.get_lambda_function<_signature...>(argsId) + ->template get_hopper(retId) + .f_ptr(); + + //assert((functor == pFunctor) && "new type-id-system not working."); pFunctor(std::forward<_signature>(params)...); return { error::None, RObject{} }; @@ -48,8 +54,14 @@ namespace rtl this is stored in _derivedType's (FunctorContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, _signature&&...params)-> Return { - decltype(pFunctor) functor = pFunctorId.get_lambda_function<_signature...>()->template get_hopper<_returnType>().f_ptr(); - assert((functor == pFunctor) && "new type-id-system not working."); + auto retId = TypeId<_returnType>::get(); + auto argsId = TypeId...>>::get(); + + decltype(pFunctor) functor = pFunctorId.get_lambda_function<_signature...>(argsId) + ->template get_hopper<_returnType>(retId) + .f_ptr(); + + //assert((functor == pFunctor) && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); @@ -89,7 +101,7 @@ namespace rtl template inline const detail::FunctorId SetupFunction<_derivedType>::addFunctor(_returnType(*pFunctor)(_signature...), std::size_t pRecordId) { - const dispatch::lambda* lambdaPtr = nullptr; + const dispatch::lambda_base* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 793ff705..fc42cb20 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -34,8 +34,15 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - auto functor = pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_hopper().f_ptr(); - assert((functor == pFunctor) && "new type-id-system not working."); + auto recId = TypeId<_recordType>::get(); + auto returnId = TypeId::get(); + auto argsId = TypeId...>>::get(); + + auto functor = pFunctorId.get_lambda_method<_recordType, _signature...>(recId, argsId) + ->template get_hopper(returnId) + .f_ptr(); + + //assert((functor == pFunctor) && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -57,8 +64,16 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - decltype(pFunctor) functor = pFunctorId.get_lambda_method<_recordType, _signature...>()->template get_hopper<_returnType>().f_ptr(); - assert((functor == pFunctor) && "new type-id-system not working."); + + auto recId = TypeId<_recordType>::get(); + auto returnId = TypeId<_returnType>::get(); + auto argsId = TypeId...>>::get(); + + decltype(pFunctor) functor = pFunctorId.get_lambda_method<_recordType, _signature...>(recId, argsId) + ->template get_hopper<_returnType>(returnId) + .f_ptr(); + + //assert((functor == pFunctor) && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -101,8 +116,15 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - decltype(pFunctor) functor = pFunctorId.get_lambda_method()->template get_hopper().f_ptr(); - assert(pFunctor == functor && "new type-id-system not working."); + auto recId = TypeId::get(); + auto returnId = TypeId::get(); + auto argsId = TypeId...>>::get(); + + decltype(pFunctor) functor = pFunctorId.get_lambda_method(recId, argsId) + ->template get_hopper(returnId) + .f_ptr(); + + //assert(pFunctor == functor && "new type-id-system not working."); const _recordType& target = pTargetObj.view<_recordType>()->get(); (target.*pFunctor)(std::forward<_signature>(params)...); @@ -120,8 +142,16 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - decltype(pFunctor) functor = pFunctorId.get_lambda_method()->template get_hopper<_returnType>().f_ptr(); - assert(pFunctor == functor && "new type-id-system not working."); + + auto recId = TypeId::get(); + auto returnId = TypeId::get(); + auto argsId = TypeId...>>::get(); + + decltype(pFunctor) functor = pFunctorId.get_lambda_method(recId, argsId) + ->template get_hopper<_returnType>(returnId) + .f_ptr(); + + //assert(pFunctor == functor && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); //'target' is const and 'pFunctor' is const-member-function. @@ -163,7 +193,7 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...)) { - const dispatch::lambda* lambdaPtr = nullptr; + const dispatch::lambda_base* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { auto& lambdaCache = cache::lambda_method<_recordType, _signature...>::instance(); @@ -234,7 +264,7 @@ namespace rtl::detail template inline const detail::FunctorId SetupMethod<_derivedType>::addFunctor(_returnType(_recordType::* pFunctor)(_signature...) const) { - const dispatch::lambda* lambdaPtr = nullptr; + const dispatch::lambda_base* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { auto& lambdaCache = cache::lambda_method<_recordType, _signature...>::instance(); diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index c0503298..eab66974 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -48,10 +48,12 @@ namespace rtl::detail template inline constexpr const HopFunction<_signature...> Hopper<>::argsT() const { + const auto argsId = TypeId>>::get(); for (auto& functorId : m_functorIds) { - if (functorId.m_lambda->is_signature<_signature...>()) [[likely]] { - return { functorId.get_lambda_function<_signature...>() }; + auto lambda = functorId.get_lambda_function<_signature...>(argsId); + if (lambda != nullptr) { + return { lambda }; } } return HopFunction<_signature...>(); @@ -64,8 +66,9 @@ namespace rtl::detail const function<_returnType(_signature...)> HopFunction<_signature...>::returnT() const { - if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) [[likely]] { - return m_lambda->template get_hopper<_returnType>(); + const auto retId = TypeId::get(); + if (m_lambda != nullptr) [[likely]] { + return m_lambda->template get_hopper<_returnType>(retId); } return function<_returnType(_signature...)>(); } diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index 5db78d47..b0c19c5c 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -44,7 +44,7 @@ namespace rtl::detail //signature of functor as string. platform dependent, may not be very much readable format. std::string m_signature; - const dispatch::lambda* m_lambda = nullptr; + const dispatch::lambda_base* m_lambda = nullptr; GETTER(std::size_t, LambdaIndex, m_lambdaIndex) GETTER(std::size_t, ReturnId, m_returnId); @@ -81,15 +81,15 @@ namespace rtl::detail } template - constexpr const dispatch::lambda_function<_signature...>* get_lambda_function() const + constexpr const dispatch::lambda_function<_signature...>* get_lambda_function(std::size_t p_argsId) const { - return m_lambda->to_function<_signature...>(); + return m_lambda->to_function<_signature...>(p_argsId); } template - constexpr const dispatch::lambda_method<_recordType, _signature...>* get_lambda_method() const + constexpr const dispatch::lambda_method<_recordType, _signature...>* get_lambda_method(std::size_t p_recordId, std::size_t p_argsId) const { - return m_lambda->to_method<_recordType, _signature...>(); + return m_lambda->to_method<_recordType, _signature...>(p_recordId, p_argsId); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index b83c1e97..5c09bf9c 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -155,12 +155,13 @@ namespace rtl::detail template inline constexpr HopMethod<_recordType, _signature...> Hopper<_recordType>::argsT() const { + const auto recId = TypeId<_recordType>::get(); + const auto argsId = TypeId>>::get(); for (auto& functorId : m_functorIds) { - if (functorId.m_lambda->is_member<_recordType>() && - functorId.m_lambda->is_signature<_signature...>()) [[likely]] - { - return { functorId.get_lambda_method<_recordType, _signature...>() }; + auto lambda = functorId.get_lambda_method<_recordType, _signature...>(recId, argsId); + if (lambda != nullptr) { + return { lambda }; } } return HopMethod<_recordType, _signature...>(); @@ -173,8 +174,10 @@ namespace rtl::detail const method<_returnType(_recordType::*)(_signature...)> HopMethod<_recordType, _signature...>::returnT() const { - if (m_lambda != nullptr && m_lambda->template is_returning<_returnType>()) { - return m_lambda->template get_hopper<_returnType>(); + if (m_lambda != nullptr) + { + const auto retId = TypeId::get(); + return m_lambda->template get_hopper<_returnType>(retId); } return method<_returnType(_recordType::*)(_signature...)>(); } diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index 06ee12a6..312bb974 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -31,11 +31,11 @@ namespace rtl::dispatch detail::methodQ m_qualifier = detail::methodQ::None; - GETTER_CPTR(lambda, _lambda, m_lambda) + GETTER_CPTR(lambda_base, _lambda, m_lambda) private: - mutable const lambda* m_lambda = nullptr; + mutable const lambda_base* m_lambda = nullptr; template friend struct cache::lambda_function; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index c3f4b1d1..16e063f1 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -16,13 +16,13 @@ namespace rtl::dispatch { - struct lambda + struct lambda_base { protected: const functor& m_functor; - lambda(const functor& p_functor) noexcept + lambda_base(const functor& p_functor) noexcept :m_functor(p_functor) { } @@ -33,15 +33,23 @@ namespace rtl::dispatch using method_t = lambda_method; template - constexpr const function_t* to_function() const + constexpr const function_t* to_function(std::size_t p_argsId) const { - return static_cast*>(this); + if (p_argsId == m_functor.m_signatureId) [[likely]] + { + return static_cast*>(this); + } + else return nullptr; } template - constexpr const method_t* to_method() const + constexpr const method_t* to_method(std::size_t p_recordId, std::size_t p_argsId) const { - return static_cast*>(this); + if (p_recordId == m_functor.m_recordId && p_argsId == m_functor.m_signatureId) [[likely]] + { + return static_cast*>(this); + } + else return nullptr; } public: diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 7b87a3fb..798d4340 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -38,7 +38,6 @@ namespace rtl return (*m_functor)(std::forward(params)...); } - private: template @@ -52,21 +51,21 @@ namespace rtl namespace rtl::dispatch { template - struct lambda_function: public lambda + struct lambda_function: public lambda_base { template using hopper_t = function; lambda_function(const functor& p_functor) noexcept - :lambda(p_functor) + :lambda_base(p_functor) { } template - constexpr const hopper_t get_hopper() const + constexpr const hopper_t get_hopper(const std::size_t p_returnId) const { - if (m_functor.m_returnId == detail::TypeId::get()) + if (p_returnId == m_functor.m_returnId) [[likely]] { - return hopper_t { + return hopper_t { static_cast&>(m_functor).f_ptr() }; } diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index 766ca007..89619e55 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -87,7 +87,7 @@ namespace rtl namespace rtl::dispatch { template - struct lambda_method : public lambda + struct lambda_method : public lambda_base { template using hopper_t = method; @@ -96,13 +96,14 @@ namespace rtl::dispatch using hopper_ct = method; lambda_method(const functor& p_functor) noexcept - :lambda(p_functor) + :lambda_base(p_functor) { } + template requires (std::is_const_v == false) - constexpr const hopper_t get_hopper() const + constexpr const hopper_t get_hopper(std::size_t p_returnId = 0) const { - if (m_functor.m_returnId == detail::TypeId::get()) + if (p_returnId == m_functor.m_returnId) [[likely]] { return hopper_t { static_cast&>(m_functor).f_ptr() @@ -111,10 +112,11 @@ namespace rtl::dispatch return hopper_t(); } + template requires (std::is_const_v == true) - constexpr const hopper_ct get_hopper() const + constexpr const hopper_ct get_hopper(std::size_t p_returnId) const { - if (m_functor.m_returnId == detail::TypeId::get()) + if (p_returnId == m_functor.m_returnId) [[likely]] { return hopper_ct { static_cast&>(m_functor).f_ptr() diff --git a/ReflectionTemplateLib/rtl/rtl_forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h index 70420b2f..84ff5eea 100644 --- a/ReflectionTemplateLib/rtl/rtl_forward_decls.h +++ b/ReflectionTemplateLib/rtl/rtl_forward_decls.h @@ -58,7 +58,7 @@ namespace rtl { struct functor; - struct lambda; + struct lambda_base; template struct lambda_function; From 0fb9e1f72e22e012181f5093010dca2dabef3c09 Mon Sep 17 00:00:00 2001 From: Neeraj Singh Date: Wed, 24 Sep 2025 17:39:51 +0000 Subject: [PATCH 37/58] fixed error and hardcoded-type bug. --- ReflectionTemplateLib/rtl/builder/SetupFunction.hpp | 4 ++-- ReflectionTemplateLib/rtl/builder/SetupMethod.hpp | 4 ++-- ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp | 4 ++-- ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp | 4 ++-- 4 files changed, 8 insertions(+), 8 deletions(-) diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index 2af99d2a..cd9357d1 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -37,7 +37,7 @@ namespace rtl ->template get_hopper(retId) .f_ptr(); - //assert((functor == pFunctor) && "new type-id-system not working."); + assert((functor == pFunctor) && "new type-id-system not working."); pFunctor(std::forward<_signature>(params)...); return { error::None, RObject{} }; @@ -61,7 +61,7 @@ namespace rtl ->template get_hopper<_returnType>(retId) .f_ptr(); - //assert((functor == pFunctor) && "new type-id-system not working."); + assert((functor == pFunctor) && "new type-id-system not working."); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index fc42cb20..e02a5b05 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -42,7 +42,7 @@ namespace rtl::detail ->template get_hopper(returnId) .f_ptr(); - //assert((functor == pFunctor) && "new type-id-system not working."); + assert((functor == pFunctor) && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -73,7 +73,7 @@ namespace rtl::detail ->template get_hopper<_returnType>(returnId) .f_ptr(); - //assert((functor == pFunctor) && "new type-id-system not working."); + assert((functor == pFunctor) && "new type-id-system not working."); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index eab66974..0bebaf34 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -48,7 +48,7 @@ namespace rtl::detail template inline constexpr const HopFunction<_signature...> Hopper<>::argsT() const { - const auto argsId = TypeId>>::get(); + const auto argsId = TypeId... >>::get(); for (auto& functorId : m_functorIds) { auto lambda = functorId.get_lambda_function<_signature...>(argsId); @@ -66,7 +66,7 @@ namespace rtl::detail const function<_returnType(_signature...)> HopFunction<_signature...>::returnT() const { - const auto retId = TypeId::get(); + const auto retId = TypeId<_returnType>::get(); if (m_lambda != nullptr) [[likely]] { return m_lambda->template get_hopper<_returnType>(retId); } diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index 5c09bf9c..348f7530 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -156,7 +156,7 @@ namespace rtl::detail inline constexpr HopMethod<_recordType, _signature...> Hopper<_recordType>::argsT() const { const auto recId = TypeId<_recordType>::get(); - const auto argsId = TypeId>>::get(); + const auto argsId = TypeId...>>::get(); for (auto& functorId : m_functorIds) { auto lambda = functorId.get_lambda_method<_recordType, _signature...>(recId, argsId); @@ -176,7 +176,7 @@ namespace rtl::detail { if (m_lambda != nullptr) { - const auto retId = TypeId::get(); + const auto retId = TypeId<_returnType>::get(); return m_lambda->template get_hopper<_returnType>(retId); } return method<_returnType(_recordType::*)(_signature...)>(); From bf495e1d3b004f0a81bef0a24ed8c507121060d6 Mon Sep 17 00:00:00 2001 From: Neeraj Singh Date: Wed, 24 Sep 2025 20:18:41 +0000 Subject: [PATCH 38/58] type erasing lambdas are stateless now. --- .../rtl/builder/SetupFunction.hpp | 36 ++++----- .../rtl/builder/SetupMethod.hpp | 74 +++++++------------ ReflectionTemplateLib/rtl/dispatch/lambda.h | 4 +- 3 files changed, 42 insertions(+), 72 deletions(-) diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index cd9357d1..d18fc575 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -28,18 +28,14 @@ namespace rtl inline SetupFunction<_derivedType>::FunctionLambda<_signature...> SetupFunction<_derivedType>::getCaller(void(*pFunctor)(_signature...)) { - return [pFunctor](const FunctorId& pFunctorId, _signature&&... params) -> Return + return [](const FunctorId& pFunctorId, _signature&&... params) -> Return { - auto retId = TypeId::get(); - auto argsId = TypeId...>>::get(); - - decltype(pFunctor) functor = pFunctorId.get_lambda_function<_signature...>(argsId) - ->template get_hopper(retId) - .f_ptr(); - - assert((functor == pFunctor) && "new type-id-system not working."); - - pFunctor(std::forward<_signature>(params)...); + auto& functorId = pFunctorId.m_lambda->m_functor; + auto fptr = pFunctorId.get_lambda_function<_signature...>(functorId.m_signatureId) + ->template get_hopper(functorId.m_returnId) + .f_ptr(); + + fptr(std::forward<_signature>(params)...); return { error::None, RObject{} }; }; } @@ -52,16 +48,12 @@ namespace rtl { /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (FunctorContainer) vector holding lambda's. - */ return [pFunctor](const FunctorId& pFunctorId, _signature&&...params)-> Return + */ return [](const FunctorId& pFunctorId, _signature&&...params)-> Return { - auto retId = TypeId<_returnType>::get(); - auto argsId = TypeId...>>::get(); - - decltype(pFunctor) functor = pFunctorId.get_lambda_function<_signature...>(argsId) - ->template get_hopper<_returnType>(retId) - .f_ptr(); - - assert((functor == pFunctor) && "new type-id-system not working."); + auto& functorId = pFunctorId.m_lambda->m_functor; + auto fptr = pFunctorId.get_lambda_function<_signature...>(functorId.m_signatureId) + ->template get_hopper<_returnType>(functorId.m_returnId) + .f_ptr(); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); @@ -69,7 +61,7 @@ namespace rtl /* if the function returns reference, this block will be retained by compiler. Note: reference to temporary or dangling is not checked here. */ using _rawRetType = traits::raw_t<_returnType>; - const _rawRetType& retObj = pFunctor(std::forward<_signature>(params)...); + const _rawRetType& retObj = fptr(std::forward<_signature>(params)...); return { error::None, RObjectBuilder::template build(&retObj, std::nullopt, isConstCastSafe) @@ -77,7 +69,7 @@ namespace rtl } else { //if the function returns anything (not refrence), this block will be retained by compiler. - auto&& retObj = pFunctor(std::forward<_signature>(params)...); + auto&& retObj = fptr(std::forward<_signature>(params)...); using T = std::remove_cvref_t; return { error::None, diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index e02a5b05..dbadadaf 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -32,24 +32,19 @@ namespace rtl::detail { /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return + */ return [](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - auto recId = TypeId<_recordType>::get(); - auto returnId = TypeId::get(); - auto argsId = TypeId...>>::get(); - - auto functor = pFunctorId.get_lambda_method<_recordType, _signature...>(recId, argsId) - ->template get_hopper(returnId) - .f_ptr(); - - assert((functor == pFunctor) && "new type-id-system not working."); + auto& functorId = pFunctorId.m_lambda->m_functor; + auto fptr = pFunctorId.get_lambda_method<_recordType, _signature...>(functorId.m_recordId, functorId.m_signatureId) + ->template get_hopper(functorId.m_returnId) + .f_ptr(); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; } _recordType& target = const_cast<_recordType&>(pTargetObj.view<_recordType>()->get()); - (target.*pFunctor)(std::forward<_signature>(params)...); + (target.*fptr)(std::forward<_signature>(params)...); return { error::None, RObject{} }; }; } @@ -62,18 +57,12 @@ namespace rtl::detail { /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return + */ return [](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - - auto recId = TypeId<_recordType>::get(); - auto returnId = TypeId<_returnType>::get(); - auto argsId = TypeId...>>::get(); - - decltype(pFunctor) functor = pFunctorId.get_lambda_method<_recordType, _signature...>(recId, argsId) - ->template get_hopper<_returnType>(returnId) - .f_ptr(); - - assert((functor == pFunctor) && "new type-id-system not working."); + auto& functorId = pFunctorId.m_lambda->m_functor; + auto fptr = pFunctorId.get_lambda_method<_recordType, _signature...>(functorId.m_recordId, functorId.m_signatureId) + ->template get_hopper<_returnType>(functorId.m_returnId) + .f_ptr(); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { return { error::IllegalConstCast, RObject{} }; @@ -87,7 +76,7 @@ namespace rtl::detail /* if the function returns reference, this block will be retained by compiler. Note: reference to temporary or dangling is not checked here. */ using _rawRetType = traits::raw_t<_returnType>; - const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + const _rawRetType& retObj = (target.*fptr)(std::forward<_signature>(params)...); return { error::None, RObjectBuilder::template build(&retObj, std::nullopt, isConstCastSafe) @@ -95,7 +84,7 @@ namespace rtl::detail } else { - auto&& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + auto&& retObj = (target.*fptr)(std::forward<_signature>(params)...); using T = std::remove_cvref_t; return { error::None, @@ -114,20 +103,15 @@ namespace rtl::detail { /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return + */ return [](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - auto recId = TypeId::get(); - auto returnId = TypeId::get(); - auto argsId = TypeId...>>::get(); - - decltype(pFunctor) functor = pFunctorId.get_lambda_method(recId, argsId) - ->template get_hopper(returnId) - .f_ptr(); - - //assert(pFunctor == functor && "new type-id-system not working."); + auto& functorId = pFunctorId.m_lambda->m_functor; + auto fptr = pFunctorId.get_lambda_method(functorId.m_recordId, functorId.m_signatureId) + ->template get_hopper(functorId.m_returnId) + .f_ptr(); const _recordType& target = pTargetObj.view<_recordType>()->get(); - (target.*pFunctor)(std::forward<_signature>(params)...); + (target.*fptr)(std::forward<_signature>(params)...); return { error::None, RObject{} }; }; } @@ -140,18 +124,12 @@ namespace rtl::detail { /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (MethodContainer) vector holding lambda's. - */ return [pFunctor](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return + */ return [](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - - auto recId = TypeId::get(); - auto returnId = TypeId::get(); - auto argsId = TypeId...>>::get(); - - decltype(pFunctor) functor = pFunctorId.get_lambda_method(recId, argsId) - ->template get_hopper<_returnType>(returnId) - .f_ptr(); - - //assert(pFunctor == functor && "new type-id-system not working."); + auto& functorId = pFunctorId.m_lambda->m_functor; + auto fptr = pFunctorId.get_lambda_method(functorId.m_recordId, functorId.m_signatureId) + ->template get_hopper<_returnType>(functorId.m_returnId) + .f_ptr(); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); //'target' is const and 'pFunctor' is const-member-function. @@ -160,7 +138,7 @@ namespace rtl::detail /* if the function returns reference, this block will be retained by compiler. Note: reference to temporary or dangling is not checked here. */ using _rawRetType = traits::raw_t<_returnType>; - const _rawRetType& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + const _rawRetType& retObj = (target.*fptr)(std::forward<_signature>(params)...); return { error::None, RObjectBuilder::template build(&retObj, std::nullopt, isConstCastSafe) @@ -168,7 +146,7 @@ namespace rtl::detail } else { - auto&& retObj = (target.*pFunctor)(std::forward<_signature>(params)...); + auto&& retObj = (target.*fptr)(std::forward<_signature>(params)...); using T = std::remove_cvref_t; return { error::None, diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index 16e063f1..4afb8a9b 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -18,9 +18,9 @@ namespace rtl::dispatch { struct lambda_base { - protected: - const functor& m_functor; + + protected: lambda_base(const functor& p_functor) noexcept :m_functor(p_functor) From cdd86768d4740b8ba1db6504519b5b9f0d748224 Mon Sep 17 00:00:00 2001 From: Neeraj Singh Date: Thu, 25 Sep 2025 06:24:25 +0000 Subject: [PATCH 39/58] new dispatch-mechanism integration. wip. --- RTLBenchmarkApp/src/StandardCall.cpp | 4 ++-- .../rtl/builder/SetupFunction.hpp | 10 ++++----- .../rtl/builder/SetupMethod.hpp | 22 ++++++++----------- .../rtl/detail/inc/FunctionCaller.hpp | 7 +++--- .../rtl/detail/inc/FunctorId.h | 4 ++-- .../rtl/detail/inc/MethodInvoker.hpp | 9 ++++---- ReflectionTemplateLib/rtl/dispatch/lambda.h | 5 +++-- .../rtl/dispatch/lambda_function.h | 4 ++-- .../rtl/dispatch/lambda_method.h | 6 ++--- 9 files changed, 32 insertions(+), 39 deletions(-) diff --git a/RTLBenchmarkApp/src/StandardCall.cpp b/RTLBenchmarkApp/src/StandardCall.cpp index 215a92d4..623b21cc 100644 --- a/RTLBenchmarkApp/src/StandardCall.cpp +++ b/RTLBenchmarkApp/src/StandardCall.cpp @@ -9,8 +9,8 @@ namespace { static auto _put_line = []() { - std::cout << "--------------------------------------------" - "----------------------------------------------------" << std::endl; + std::cout << "------------------------------------------" + "--------------------------------------------------" << std::endl; return 0; }; diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index d18fc575..ce32d60f 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -30,9 +30,8 @@ namespace rtl { return [](const FunctorId& pFunctorId, _signature&&... params) -> Return { - auto& functorId = pFunctorId.m_lambda->m_functor; - auto fptr = pFunctorId.get_lambda_function<_signature...>(functorId.m_signatureId) - ->template get_hopper(functorId.m_returnId) + auto fptr = pFunctorId.get_lambda_function<_signature...>() + ->template get_hopper() .f_ptr(); fptr(std::forward<_signature>(params)...); @@ -50,9 +49,8 @@ namespace rtl this is stored in _derivedType's (FunctorContainer) vector holding lambda's. */ return [](const FunctorId& pFunctorId, _signature&&...params)-> Return { - auto& functorId = pFunctorId.m_lambda->m_functor; - auto fptr = pFunctorId.get_lambda_function<_signature...>(functorId.m_signatureId) - ->template get_hopper<_returnType>(functorId.m_returnId) + auto fptr = pFunctorId.get_lambda_function<_signature...>() + ->template get_hopper<_returnType>() .f_ptr(); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index dbadadaf..08c1e9d2 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -33,10 +33,9 @@ namespace rtl::detail /* a variable arguments lambda, which finally calls the 'pFunctor' with 'params...'. this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return - { - auto& functorId = pFunctorId.m_lambda->m_functor; - auto fptr = pFunctorId.get_lambda_method<_recordType, _signature...>(functorId.m_recordId, functorId.m_signatureId) - ->template get_hopper(functorId.m_returnId) + { + auto fptr = pFunctorId.get_lambda_method<_recordType, _signature...>() + ->template get_hopper() .f_ptr(); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { @@ -59,9 +58,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - auto& functorId = pFunctorId.m_lambda->m_functor; - auto fptr = pFunctorId.get_lambda_method<_recordType, _signature...>(functorId.m_recordId, functorId.m_signatureId) - ->template get_hopper<_returnType>(functorId.m_returnId) + auto fptr = pFunctorId.get_lambda_method<_recordType, _signature...>() + ->template get_hopper<_returnType>() .f_ptr(); if (!pTargetObj.isConstCastSafe()) [[unlikely]] { @@ -105,9 +103,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - auto& functorId = pFunctorId.m_lambda->m_functor; - auto fptr = pFunctorId.get_lambda_method(functorId.m_recordId, functorId.m_signatureId) - ->template get_hopper(functorId.m_returnId) + auto fptr = pFunctorId.get_lambda_method() + ->template get_hopper() .f_ptr(); const _recordType& target = pTargetObj.view<_recordType>()->get(); @@ -126,9 +123,8 @@ namespace rtl::detail this is stored in _derivedType's (MethodContainer) vector holding lambda's. */ return [](const FunctorId& pFunctorId, const RObject& pTargetObj, _signature&&...params)-> Return { - auto& functorId = pFunctorId.m_lambda->m_functor; - auto fptr = pFunctorId.get_lambda_method(functorId.m_recordId, functorId.m_signatureId) - ->template get_hopper<_returnType>(functorId.m_returnId) + auto fptr = pFunctorId.get_lambda_method() + ->template get_hopper<_returnType>() .f_ptr(); constexpr bool isConstCastSafe = (!traits::is_const_v<_returnType>); diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index 0bebaf34..af125bd2 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -52,7 +52,7 @@ namespace rtl::detail for (auto& functorId : m_functorIds) { auto lambda = functorId.get_lambda_function<_signature...>(argsId); - if (lambda != nullptr) { + if (lambda != nullptr) [[likely]] { return { lambda }; } } @@ -62,9 +62,8 @@ namespace rtl::detail template template - inline constexpr - const function<_returnType(_signature...)> - HopFunction<_signature...>::returnT() const + inline constexpr const function<_returnType(_signature...)> + HopFunction<_signature...>::returnT() const { const auto retId = TypeId<_returnType>::get(); if (m_lambda != nullptr) [[likely]] { diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index b0c19c5c..2761736c 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -81,13 +81,13 @@ namespace rtl::detail } template - constexpr const dispatch::lambda_function<_signature...>* get_lambda_function(std::size_t p_argsId) const + constexpr const dispatch::lambda_function<_signature...>* get_lambda_function(std::size_t p_argsId = 0) const { return m_lambda->to_function<_signature...>(p_argsId); } template - constexpr const dispatch::lambda_method<_recordType, _signature...>* get_lambda_method(std::size_t p_recordId, std::size_t p_argsId) const + constexpr const dispatch::lambda_method<_recordType, _signature...>* get_lambda_method(std::size_t p_recordId = 0, std::size_t p_argsId = 0) const { return m_lambda->to_method<_recordType, _signature...>(p_recordId, p_argsId); } diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index 348f7530..6f7d9074 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -160,7 +160,7 @@ namespace rtl::detail for (auto& functorId : m_functorIds) { auto lambda = functorId.get_lambda_method<_recordType, _signature...>(recId, argsId); - if (lambda != nullptr) { + if (lambda != nullptr) [[likely]] { return { lambda }; } } @@ -170,11 +170,10 @@ namespace rtl::detail template template - inline constexpr - const method<_returnType(_recordType::*)(_signature...)> - HopMethod<_recordType, _signature...>::returnT() const + inline constexpr const method<_returnType(_recordType::*)(_signature...)> + HopMethod<_recordType, _signature...>::returnT() const { - if (m_lambda != nullptr) + if (m_lambda != nullptr) [[likely]] { const auto retId = TypeId<_returnType>::get(); return m_lambda->template get_hopper<_returnType>(retId); diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index 4afb8a9b..a1467bc7 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -35,7 +35,7 @@ namespace rtl::dispatch template constexpr const function_t* to_function(std::size_t p_argsId) const { - if (p_argsId == m_functor.m_signatureId) [[likely]] + if (p_argsId == 0 || p_argsId == m_functor.m_signatureId) [[likely]] { return static_cast*>(this); } @@ -45,7 +45,8 @@ namespace rtl::dispatch template constexpr const method_t* to_method(std::size_t p_recordId, std::size_t p_argsId) const { - if (p_recordId == m_functor.m_recordId && p_argsId == m_functor.m_signatureId) [[likely]] + if (p_recordId == 0 || p_argsId ==0 || + (p_recordId == m_functor.m_recordId && p_argsId == m_functor.m_signatureId)) [[likely]] { return static_cast*>(this); } diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 798d4340..ade3aef1 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -61,9 +61,9 @@ namespace rtl::dispatch { } template - constexpr const hopper_t get_hopper(const std::size_t p_returnId) const + constexpr const hopper_t get_hopper(const std::size_t p_returnId = 0) const { - if (p_returnId == m_functor.m_returnId) [[likely]] + if (p_returnId == 0 || p_returnId == m_functor.m_returnId) [[likely]] { return hopper_t { static_cast&>(m_functor).f_ptr() diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index 89619e55..5f0f03ff 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -103,7 +103,7 @@ namespace rtl::dispatch template requires (std::is_const_v == false) constexpr const hopper_t get_hopper(std::size_t p_returnId = 0) const { - if (p_returnId == m_functor.m_returnId) [[likely]] + if (p_returnId == 0 || p_returnId == m_functor.m_returnId) [[likely]] { return hopper_t { static_cast&>(m_functor).f_ptr() @@ -114,9 +114,9 @@ namespace rtl::dispatch template requires (std::is_const_v == true) - constexpr const hopper_ct get_hopper(std::size_t p_returnId) const + constexpr const hopper_ct get_hopper(std::size_t p_returnId = 0) const { - if (p_returnId == m_functor.m_returnId) [[likely]] + if (p_returnId == 0 || p_returnId == m_functor.m_returnId) [[likely]] { return hopper_ct { static_cast&>(m_functor).f_ptr() From e14381fc427fb5d9347865bfcb696af27b755cd5 Mon Sep 17 00:00:00 2001 From: neeraj Date: Thu, 25 Sep 2025 20:35:59 +0530 Subject: [PATCH 40/58] return-type reased dispatch, wip. --- ReflectionTemplateLib/CMakeLists.txt | 2 +- .../rtl/dispatch/CMakeLists.txt | 4 ++ .../rtl/dispatch/lambda_function.h | 35 +-------- .../rtl/dispatch/lambda_method.h | 72 +------------------ .../rtl/dispatch/rtl_const_method.h | 50 +++++++++++++ .../rtl/dispatch/rtl_function.h | 49 +++++++++++++ .../rtl/dispatch/rtl_method.h | 50 +++++++++++++ .../rtl/erasure/CMakeLists.txt | 9 +++ .../rtl/erasure/erasure_function.h | 26 +++++++ ReflectionTemplateLib/rtl/rtl_forward_decls.h | 9 +++ 10 files changed, 201 insertions(+), 105 deletions(-) create mode 100644 ReflectionTemplateLib/rtl/dispatch/rtl_const_method.h create mode 100644 ReflectionTemplateLib/rtl/dispatch/rtl_function.h create mode 100644 ReflectionTemplateLib/rtl/dispatch/rtl_method.h create mode 100644 ReflectionTemplateLib/rtl/erasure/CMakeLists.txt create mode 100644 ReflectionTemplateLib/rtl/erasure/erasure_function.h diff --git a/ReflectionTemplateLib/CMakeLists.txt b/ReflectionTemplateLib/CMakeLists.txt index 24defcf1..ce4f2db7 100644 --- a/ReflectionTemplateLib/CMakeLists.txt +++ b/ReflectionTemplateLib/CMakeLists.txt @@ -18,7 +18,7 @@ target_include_directories(${PROJECT_NAME} ${CMAKE_CURRENT_SOURCE_DIR}/rtl/cache ${CMAKE_CURRENT_SOURCE_DIR}/rtl/detail ${CMAKE_CURRENT_SOURCE_DIR}/rtl/dispatch - ${CMAKE_CURRENT_SOURCE_DIR}/rtl/registry + ${CMAKE_CURRENT_SOURCE_DIR}/rtl/erasure ${CMAKE_CURRENT_SOURCE_DIR}/rtl/inc ${CMAKE_CURRENT_SOURCE_DIR}/rtl ) diff --git a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt index d1c8956b..cf3b911f 100644 --- a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt @@ -11,6 +11,10 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/lambda.h" "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method.h" "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function.h" + + "${CMAKE_CURRENT_SOURCE_DIR}/rtl_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/rtl_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/rtl_const_method.h" ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index ade3aef1..fd85d9b8 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -13,40 +13,7 @@ #include "lambda.h" #include "function_ptr.h" - -namespace rtl -{ - template - struct function - { - using fptr_t = return_t(*)(signature_ts...); - - const fptr_t m_functor = nullptr; - - constexpr auto f_ptr() const { - return m_functor; - } - - constexpr operator bool() const { - return (m_functor != nullptr); - } - - template - [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept(noexcept_v) - { - static_assert(is_args_t_ok, "Argument types don't match the expected signature."); - return (*m_functor)(std::forward(params)...); - } - - private: - - template - static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - - template - static constexpr bool noexcept_v = noexcept(std::declval()(std::declval()...)); - }; -} +#include "rtl_function.h" namespace rtl::dispatch { diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index 5f0f03ff..b7b24fb5 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -13,76 +13,8 @@ #include "lambda.h" #include "method_ptr.h" - -namespace rtl -{ - template - struct method - { - using fptr_t = return_t (record_t::*)(signature_ts...); - - const fptr_t m_functor = nullptr; - - constexpr auto f_ptr() const { - return m_functor; - } - - constexpr operator bool() const { - return (m_functor != nullptr); - } - - template - [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept(noexcept_v) - { - static_assert(is_args_t_ok, "Argument types don't match the expected signature."); - return (target.*m_functor)(std::forward(params)...); - } - - private: - - template - static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - - template - static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); - }; -} - - -namespace rtl -{ - template - struct method - { - using fptr_t = return_t(record_t::*)(signature_ts...) const; - - const fptr_t m_functor = nullptr; - - constexpr auto f_ptr() const { - return m_functor; - } - - constexpr operator bool() const { - return (m_functor != nullptr); - } - - template - [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept(noexcept_v) - { - static_assert(is_args_t_ok, "Argument types don't match the expected signature."); - return (target.*m_functor)(std::forward(params)...); - } - - private: - - template - static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - - template - static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); - }; -} - +#include "rtl_method.h" +#include "rtl_const_method.h" namespace rtl::dispatch { diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_const_method.h b/ReflectionTemplateLib/rtl/dispatch/rtl_const_method.h new file mode 100644 index 00000000..62da2180 --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_const_method.h @@ -0,0 +1,50 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "rtl_traits.h" +#include "rtl_forward_decls.h" + + +namespace rtl +{ + template + struct method + { + using fptr_t = return_t(record_t::*)(signature_ts...) const; + + const fptr_t m_functor = nullptr; + + constexpr auto f_ptr() const { + return m_functor; + } + + constexpr operator bool() const { + return (m_functor != nullptr); + } + + template + [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept(noexcept_v) + { + static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + return (target.*m_functor)(std::forward(params)...); + } + + private: + + template + static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; + + template + static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h new file mode 100644 index 00000000..ed81c7c6 --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h @@ -0,0 +1,49 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "rtl_traits.h" +#include "rtl_forward_decls.h" + +namespace rtl +{ + template + struct function + { + using fptr_t = return_t(*)(signature_ts...); + + const fptr_t m_functor = nullptr; + + constexpr auto f_ptr() const { + return m_functor; + } + + constexpr operator bool() const { + return (m_functor != nullptr); + } + + template + [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept(noexcept_v) + { + static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + return (*m_functor)(std::forward(params)...); + } + + private: + + template + static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; + + template + static constexpr bool noexcept_v = noexcept(std::declval()(std::declval()...)); + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h new file mode 100644 index 00000000..27e9912c --- /dev/null +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h @@ -0,0 +1,50 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "rtl_traits.h" +#include "rtl_forward_decls.h" + + +namespace rtl +{ + template + struct method + { + using fptr_t = return_t (record_t::*)(signature_ts...); + + const fptr_t m_functor = nullptr; + + constexpr auto f_ptr() const { + return m_functor; + } + + constexpr operator bool() const { + return (m_functor != nullptr); + } + + template + [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept(noexcept_v) + { + static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + return (target.*m_functor)(std::forward(params)...); + } + + private: + + template + static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; + + template + static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt b/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt new file mode 100644 index 00000000..bd5acdb2 --- /dev/null +++ b/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt @@ -0,0 +1,9 @@ +# ReflectionTemplateLibrary-CPP/ReflectionTemplateLib/erasure/CMakeLists.txt + +# Collect headers in this folder (absolute paths) +set(LOCAL_HEADERS + "${CMAKE_CURRENT_SOURCE_DIR}/erasure_function.h" +) + +target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) +source_group("Header Files\\Erasure" FILES ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/erasure/erasure_function.h b/ReflectionTemplateLib/rtl/erasure/erasure_function.h new file mode 100644 index 00000000..6ee85387 --- /dev/null +++ b/ReflectionTemplateLib/rtl/erasure/erasure_function.h @@ -0,0 +1,26 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + + +// #include "RObject.h" +// #include "rtl_traits.h" +// #include "rtl_forward_decls.h" + +// namespace rtl::erasure +// { +// template +// struct function +// { +// virtual Return +// }; +// } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/rtl_forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h index 84ff5eea..4f3c4e95 100644 --- a/ReflectionTemplateLib/rtl/rtl_forward_decls.h +++ b/ReflectionTemplateLib/rtl/rtl_forward_decls.h @@ -31,6 +31,15 @@ namespace rtl template struct method; + namespace erasure + { + template + struct function; + + template + struct method; + } + namespace detail { struct FunctorId; From cf8900711a2bf933fc221657790bda7c02d45d92 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Fri, 26 Sep 2025 01:45:34 +0530 Subject: [PATCH 41/58] erasure_base, wip. --- ReflectionTemplateLib/rtl/CMakeLists.txt | 1 + .../rtl/erasure/erasure_function.h | 33 ++++++++++++------- ReflectionTemplateLib/rtl/rtl_forward_decls.h | 5 ++- 3 files changed, 26 insertions(+), 13 deletions(-) diff --git a/ReflectionTemplateLib/rtl/CMakeLists.txt b/ReflectionTemplateLib/rtl/CMakeLists.txt index dd7b3895..daa071c9 100644 --- a/ReflectionTemplateLib/rtl/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/CMakeLists.txt @@ -19,4 +19,5 @@ add_subdirectory(src) add_subdirectory(builder) add_subdirectory(cache) add_subdirectory(detail) +add_subdirectory(erasure) add_subdirectory(dispatch) \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erasure_function.h b/ReflectionTemplateLib/rtl/erasure/erasure_function.h index 6ee85387..aa3ab9a8 100644 --- a/ReflectionTemplateLib/rtl/erasure/erasure_function.h +++ b/ReflectionTemplateLib/rtl/erasure/erasure_function.h @@ -4,7 +4,7 @@ * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * * * * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * + * SPDX-License-Identifier: MIT * * * *************************************************************************/ @@ -12,15 +12,24 @@ #pragma once -// #include "RObject.h" -// #include "rtl_traits.h" -// #include "rtl_forward_decls.h" + #include "RObject.h" + #include "rtl_traits.h" + #include "rtl_forward_decls.h" -// namespace rtl::erasure -// { -// template -// struct function -// { -// virtual Return -// }; -// } \ No newline at end of file + namespace rtl::erase + { + template + struct erasure_base + { + virtual Return forward(signature_ts&&...) = 0; + }; + + template + struct function_return : public erasure_base + { + Return forward(signature_ts&&...) override + { + return Return{ error::None, RObject{ return_t() } }; + } + }; + } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/rtl_forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h index 4f3c4e95..3132fb24 100644 --- a/ReflectionTemplateLib/rtl/rtl_forward_decls.h +++ b/ReflectionTemplateLib/rtl/rtl_forward_decls.h @@ -31,8 +31,11 @@ namespace rtl template struct method; - namespace erasure + namespace erase { + //template + //struct erasure_base; + template struct function; From 09d5b6cb40377babd6aa50faaf54c04c1bea69cd Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Fri, 26 Sep 2025 01:52:02 +0530 Subject: [PATCH 42/58] fixed last incomplete commit --- ReflectionTemplateLib/rtl/erasure/erasure_function.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/ReflectionTemplateLib/rtl/erasure/erasure_function.h b/ReflectionTemplateLib/rtl/erasure/erasure_function.h index aa3ab9a8..8525e87f 100644 --- a/ReflectionTemplateLib/rtl/erasure/erasure_function.h +++ b/ReflectionTemplateLib/rtl/erasure/erasure_function.h @@ -19,13 +19,13 @@ namespace rtl::erase { template - struct erasure_base + struct erasure_base { virtual Return forward(signature_ts&&...) = 0; }; template - struct function_return : public erasure_base + struct function_return : public erasure_base { Return forward(signature_ts&&...) override { From 3ad119b43cf5699a0bcce8d7a60b4063cb5d417a Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Fri, 26 Sep 2025 11:22:24 +0530 Subject: [PATCH 43/58] return erased, wip. --- .../rtl/erasure/CMakeLists.txt | 3 +- .../rtl/erasure/erase_return.h | 64 +++++++++++++++++++ .../erasure/{erasure_function.h => erasure.h} | 32 +++------- ReflectionTemplateLib/rtl/rtl_forward_decls.h | 4 +- 4 files changed, 78 insertions(+), 25 deletions(-) create mode 100644 ReflectionTemplateLib/rtl/erasure/erase_return.h rename ReflectionTemplateLib/rtl/erasure/{erasure_function.h => erasure.h} (56%) diff --git a/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt b/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt index bd5acdb2..03494399 100644 --- a/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt @@ -2,7 +2,8 @@ # Collect headers in this folder (absolute paths) set(LOCAL_HEADERS - "${CMAKE_CURRENT_SOURCE_DIR}/erasure_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/erasure.h" + "${CMAKE_CURRENT_SOURCE_DIR}/erase_return.h" ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/erasure/erase_return.h b/ReflectionTemplateLib/rtl/erasure/erase_return.h new file mode 100644 index 00000000..ef250ada --- /dev/null +++ b/ReflectionTemplateLib/rtl/erasure/erase_return.h @@ -0,0 +1,64 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + + +#include "erasure.h" +#include "rtl_traits.h" +#include "rtl_function.h" +#include "RObjectBuilder.hpp" + +namespace rtl::erase +{ + template + struct function_return : public erasure_base + { + rtl::function m_function; + + Return forward(signature_ts&&...params) override + { + if constexpr (std::is_void_v) + { + m_function(std::forward(params)...); + return { error::None, RObject{} }; + } + else + { + constexpr bool isConstCastSafe = (!traits::is_const_v); + + if constexpr (std::is_reference_v) { + + auto& retObj = m_function(std::forward(params)...); + + using T = std::remove_cvref_t; + return Return { + error::None, + detail::RObjectBuilder::template + build(&retObj, std::nullopt, isConstCastSafe) + }; + } + else + { + auto&& retObj = fptr(std::forward(params)...); + + using T = std::remove_cvref_t; + return Return { + error::None, + detail::RObjectBuilder::template + build(std::forward(retObj), std::nullopt, isConstCastSafe) + }; + } + } + return Return{ error::None, RObject{} }; + } + }; + } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erasure_function.h b/ReflectionTemplateLib/rtl/erasure/erasure.h similarity index 56% rename from ReflectionTemplateLib/rtl/erasure/erasure_function.h rename to ReflectionTemplateLib/rtl/erasure/erasure.h index 8525e87f..70695683 100644 --- a/ReflectionTemplateLib/rtl/erasure/erasure_function.h +++ b/ReflectionTemplateLib/rtl/erasure/erasure.h @@ -4,32 +4,20 @@ * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * * * * Copyright (c) 2025 Neeraj Singh * - * SPDX-License-Identifier: MIT * + * SPDX-License-Identifier: MIT * * * *************************************************************************/ #pragma once +#include "rtl_forward_decls.h" - #include "RObject.h" - #include "rtl_traits.h" - #include "rtl_forward_decls.h" - - namespace rtl::erase - { - template - struct erasure_base - { - virtual Return forward(signature_ts&&...) = 0; - }; - - template - struct function_return : public erasure_base - { - Return forward(signature_ts&&...) override - { - return Return{ error::None, RObject{ return_t() } }; - } - }; - } \ No newline at end of file +namespace rtl::erase +{ + template + struct erasure_base + { + virtual rtl::Return forward(signature_ts&&...) = 0; + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/rtl_forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h index 3132fb24..e7b962ed 100644 --- a/ReflectionTemplateLib/rtl/rtl_forward_decls.h +++ b/ReflectionTemplateLib/rtl/rtl_forward_decls.h @@ -33,8 +33,8 @@ namespace rtl namespace erase { - //template - //struct erasure_base; + template + struct erasure_base; template struct function; From 8937d9c4282b0cf55cf3373197546c72518be4b5 Mon Sep 17 00:00:00 2001 From: Neeraj Singh Date: Sat, 27 Sep 2025 14:08:33 +0000 Subject: [PATCH 44/58] return erased, wip. --- .../rtl/builder/SetupFunction.hpp | 2 +- .../rtl/cache/cache_lambda_function.h | 11 +++- ReflectionTemplateLib/rtl/dispatch/functor.h | 2 +- ReflectionTemplateLib/rtl/dispatch/lambda.h | 4 +- .../rtl/dispatch/lambda_function.h | 22 +++++--- .../rtl/dispatch/rtl_function.h | 19 +++++-- .../rtl/erasure/erase_return.h | 54 ++++--------------- ReflectionTemplateLib/rtl/erasure/erasure.h | 2 +- ReflectionTemplateLib/rtl/rtl_forward_decls.h | 2 +- 9 files changed, 58 insertions(+), 60 deletions(-) diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index ce32d60f..8794ec85 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -95,7 +95,7 @@ namespace rtl const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = cache::lambda_function<_signature...>::instance(); + auto& lambdaCache = cache::lambda_function<_returnType, _signature...>::instance(); auto& functorCache = cache::function_ptr<_returnType, _signature...>::instance(); auto& functor = functorCache.push(pFunctor, pIndex); diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h index 0bc1ed17..a83566e0 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h @@ -14,10 +14,11 @@ #include #include "lambda_function.h" +#include "erase_return.h" namespace rtl::cache { - template + template struct lambda_function { static const lambda_function& instance() @@ -28,8 +29,13 @@ namespace rtl::cache const dispatch::lambda_function& push(const dispatch::functor& fptr) const { - m_cache.push_back(dispatch::lambda_function(fptr)); + m_erasure_cache.push_back(erase::function_return()); + erase::erasure_base* erasure = &m_erasure_cache.back(); + + m_cache.push_back(dispatch::lambda_function(fptr, erasure)); fptr.m_lambda = &m_cache.back(); + + (m_cache.back()).template init_erasure(); return m_cache.back(); } @@ -42,6 +48,7 @@ namespace rtl::cache // No reallocation occurs; original objects stay intact mutable std::list> m_cache; + mutable std::list> m_erasure_cache; lambda_function() = default; }; diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index 312bb974..070c4a59 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -37,7 +37,7 @@ namespace rtl::dispatch mutable const lambda_base* m_lambda = nullptr; - template + template friend struct cache::lambda_function; template diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index a1467bc7..06ec3000 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -20,7 +20,7 @@ namespace rtl::dispatch { const functor& m_functor; - protected: +// protected: lambda_base(const functor& p_functor) noexcept :m_functor(p_functor) @@ -53,7 +53,7 @@ namespace rtl::dispatch else return nullptr; } - public: +// public: GETTER_CREF(functor, _functor, m_functor); diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index fd85d9b8..426239fb 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -14,6 +14,7 @@ #include "lambda.h" #include "function_ptr.h" #include "rtl_function.h" +#include "erase_return.h" namespace rtl::dispatch { @@ -21,20 +22,29 @@ namespace rtl::dispatch struct lambda_function: public lambda_base { template - using hopper_t = function; + using hopper_t = rtl::function; - lambda_function(const functor& p_functor) noexcept - :lambda_base(p_functor) + erase::erasure_base* m_erasure; + + lambda_function(const functor& p_functor, erase::erasure_base* p_erasure) noexcept + : lambda_base(p_functor) + , m_erasure(p_erasure) { } + template + constexpr void init_erasure() const + { + auto erasure = static_cast*>(m_erasure); + erasure->m_function = get_hopper(); + } + template constexpr const hopper_t get_hopper(const std::size_t p_returnId = 0) const { if (p_returnId == 0 || p_returnId == m_functor.m_returnId) [[likely]] { - return hopper_t { - static_cast&>(m_functor).f_ptr() - }; + auto fptr = static_cast&>(m_functor).f_ptr(); + return hopper_t(fptr); } return hopper_t(); } diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h index ed81c7c6..e8fd153e 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h @@ -21,8 +21,6 @@ namespace rtl { using fptr_t = return_t(*)(signature_ts...); - const fptr_t m_functor = nullptr; - constexpr auto f_ptr() const { return m_functor; } @@ -38,12 +36,27 @@ namespace rtl return (*m_functor)(std::forward(params)...); } + function(fptr_t p_functor): m_functor(p_functor) + { } + + function() = default; + function(function&&) = default; + function(const function&) = default; + + function& operator=(function&&) = default; + function& operator=(const function&) = default; + private: + fptr_t m_functor = nullptr; + template static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; template static constexpr bool noexcept_v = noexcept(std::declval()(std::declval()...)); + + template + friend struct dispatch::lambda_function; }; -} \ No newline at end of file +} diff --git a/ReflectionTemplateLib/rtl/erasure/erase_return.h b/ReflectionTemplateLib/rtl/erasure/erase_return.h index ef250ada..5dd4136b 100644 --- a/ReflectionTemplateLib/rtl/erasure/erase_return.h +++ b/ReflectionTemplateLib/rtl/erasure/erase_return.h @@ -15,50 +15,18 @@ #include "erasure.h" #include "rtl_traits.h" #include "rtl_function.h" -#include "RObjectBuilder.hpp" +#include "rtl_errors.h" namespace rtl::erase { - template - struct function_return : public erasure_base - { - rtl::function m_function; - - Return forward(signature_ts&&...params) override - { - if constexpr (std::is_void_v) - { - m_function(std::forward(params)...); - return { error::None, RObject{} }; - } - else - { - constexpr bool isConstCastSafe = (!traits::is_const_v); - - if constexpr (std::is_reference_v) { - - auto& retObj = m_function(std::forward(params)...); - - using T = std::remove_cvref_t; - return Return { - error::None, - detail::RObjectBuilder::template - build(&retObj, std::nullopt, isConstCastSafe) - }; - } - else - { - auto&& retObj = fptr(std::forward(params)...); - - using T = std::remove_cvref_t; - return Return { - error::None, - detail::RObjectBuilder::template - build(std::forward(retObj), std::nullopt, isConstCastSafe) - }; - } - } - return Return{ error::None, RObject{} }; - } - }; + template + struct function_return : public erasure_base + { + rtl::function m_function; + + void forward(signature_ts&&...params) override + { + //m_function(std::forward(params)...); + } + }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erasure.h b/ReflectionTemplateLib/rtl/erasure/erasure.h index 70695683..9866bd6d 100644 --- a/ReflectionTemplateLib/rtl/erasure/erasure.h +++ b/ReflectionTemplateLib/rtl/erasure/erasure.h @@ -18,6 +18,6 @@ namespace rtl::erase template struct erasure_base { - virtual rtl::Return forward(signature_ts&&...) = 0; + virtual void forward(signature_ts&&...) = 0; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/rtl_forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h index e7b962ed..36e30570 100644 --- a/ReflectionTemplateLib/rtl/rtl_forward_decls.h +++ b/ReflectionTemplateLib/rtl/rtl_forward_decls.h @@ -59,7 +59,7 @@ namespace rtl namespace cache { - template + template struct lambda_function; template From 7531afa59a2ec3d955b427adeee9e7a37f0a8a2d Mon Sep 17 00:00:00 2001 From: neeraj Date: Sun, 28 Sep 2025 00:27:20 +0530 Subject: [PATCH 45/58] erased return calls in benchmarks, wip. --- .../src/ReflectedCallUnknownReturn.cpp | 14 +++++- RTLBenchmarkApp/src/StandardCall.cpp | 3 +- RTLBenchmarkApp/src/StdFunction.cpp | 9 ++-- .../rtl/dispatch/lambda_function.h | 6 +++ .../rtl/dispatch/rtl_function.h | 2 +- .../rtl/erasure/erase_return.h | 18 +++++-- ReflectionTemplateLib/rtl/erasure/erasure.h | 4 +- ReflectionTemplateLib/rtl/inc/Function.h | 11 +++++ ReflectionTemplateLib/rtl/inc/Function.hpp | 47 +++++++++++++++++++ ReflectionTemplateLib/rtl/rtl_typeid.h | 10 +++- 10 files changed, 112 insertions(+), 12 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index 119e5eff..468afbb9 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -5,6 +5,11 @@ #include "BenchMark.h" #include "ReflectedCallUnknownReturn.h" +namespace bm +{ + extern std::optional g_work_done; +} + namespace cxx { extern const rtl::CxxMirror& mirror(); @@ -154,7 +159,10 @@ void RtlFunction_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) static auto _ = _test1(); for (auto _ : state) { - benchmark::DoNotOptimize(NodeSendMessage(nodeObj)(bm::g_longStr)); + //Testings: + SendMessage.ecall_v(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); + //benchmark::DoNotOptimize(NodeSendMessage(nodeObj)(bm::g_longStr)); } } @@ -164,6 +172,8 @@ void RtlFunction_callMethod_ReturnUnknown::typeNonVoid(benchmark::State& state) static auto _ = _test3(); for (auto _ : state) { - benchmark::DoNotOptimize(NodeGetMessage(nodeObj)(bm::g_longStr)); + //Testing: + benchmark::DoNotOptimize(GetMessage.ecall_r(bm::g_longStr)); + //benchmark::DoNotOptimize(NodeGetMessage(nodeObj)(bm::g_longStr)); } } \ No newline at end of file diff --git a/RTLBenchmarkApp/src/StandardCall.cpp b/RTLBenchmarkApp/src/StandardCall.cpp index 623b21cc..30de3b2c 100644 --- a/RTLBenchmarkApp/src/StandardCall.cpp +++ b/RTLBenchmarkApp/src/StandardCall.cpp @@ -1,4 +1,5 @@ +#include #include #include #include @@ -33,7 +34,7 @@ namespace bm extern std::function NodeSendMessage; - extern std::function GetMessage; + extern std::function GetMessage; extern std::function NodeGetMessage; } diff --git a/RTLBenchmarkApp/src/StdFunction.cpp b/RTLBenchmarkApp/src/StdFunction.cpp index f3998942..c8d5647c 100644 --- a/RTLBenchmarkApp/src/StdFunction.cpp +++ b/RTLBenchmarkApp/src/StdFunction.cpp @@ -1,4 +1,5 @@ +#include #include #include "BenchMark.h" @@ -33,10 +34,12 @@ namespace bm pNode.sendMessage(pMsg); }; - std::function GetMessage = [](bm::argStr_t& pMsg) + std::function GetMessage = [](bm::argStr_t& pMsg) { - auto retMsg = bm::getMessage(pMsg); - return retMsg; + //Testing. + return std::any(bm::getMessage(pMsg)); + // auto retMsg = bm::getMessage(pMsg); + // return retMsg; }; std::function NodeGetMessage = [](bm::Node pNode, bm::argStr_t& pMsg) diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 426239fb..14a90ded 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -48,5 +48,11 @@ namespace rtl::dispatch } return hopper_t(); } + + template + constexpr decltype(auto) operator()(args_t&&...params) const + { + return m_erasure->forward(std::forward(params)...); + } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h index e8fd153e..14ada51e 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h @@ -32,7 +32,7 @@ namespace rtl template [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept(noexcept_v) { - static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (*m_functor)(std::forward(params)...); } diff --git a/ReflectionTemplateLib/rtl/erasure/erase_return.h b/ReflectionTemplateLib/rtl/erasure/erase_return.h index 5dd4136b..0f880333 100644 --- a/ReflectionTemplateLib/rtl/erasure/erase_return.h +++ b/ReflectionTemplateLib/rtl/erasure/erase_return.h @@ -11,11 +11,11 @@ #pragma once - #include "erasure.h" #include "rtl_traits.h" #include "rtl_function.h" #include "rtl_errors.h" +#include namespace rtl::erase { @@ -24,9 +24,21 @@ namespace rtl::erase { rtl::function m_function; - void forward(signature_ts&&...params) override + void hop_v(signature_ts&&...params) const noexcept override + { + if constexpr (std::is_void_v) + { + m_function(std::forward(params)...); + } + } + + std::any hop_r(signature_ts&&...params) const noexcept override { - //m_function(std::forward(params)...); + if constexpr (!std::is_void_v) + { + return std::any(m_function(std::forward(params)...)); + } + else return std::any(); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erasure.h b/ReflectionTemplateLib/rtl/erasure/erasure.h index 9866bd6d..57cb6ea9 100644 --- a/ReflectionTemplateLib/rtl/erasure/erasure.h +++ b/ReflectionTemplateLib/rtl/erasure/erasure.h @@ -11,6 +11,7 @@ #pragma once +#include #include "rtl_forward_decls.h" namespace rtl::erase @@ -18,6 +19,7 @@ namespace rtl::erase template struct erasure_base { - virtual void forward(signature_ts&&...) = 0; + virtual void hop_v(signature_ts&&...) const noexcept = 0; + virtual std::any hop_r(signature_ts&&...) const noexcept = 0; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 3bdab774..a08aade2 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -11,14 +11,17 @@ #pragma once +#include #include #include #include #include "FunctorId.h" +#include "RObject.h" #include "rtl_constants.h" #include "FunctionCaller.h" #include "lambda_function.h" +#include "rtl_errors.h" namespace rtl { @@ -70,6 +73,8 @@ namespace rtl { const detail::FunctorId* hasFunctorId(const std::size_t pSignatureId) const; + const detail::FunctorId* getLambdaById(const std::size_t pSignatureId) const; + GETTER(detail::methodQ, Qualifier, m_qualifier); GETTER_REF(std::vector, FunctorIds, m_functorIds) @@ -102,6 +107,12 @@ namespace rtl { template constexpr const detail::FunctionCaller<_signature...> bind() const noexcept; + template + rtl::error ecall_v(_args&&...) const noexcept; + + template + std::any ecall_r(_args&&...) const noexcept; + friend detail::CxxReflection; friend detail::ReflectionBuilder; diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index a102d50b..49a531d5 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -13,6 +13,14 @@ #include "Function.h" #include "FunctionCaller.hpp" +#include "RObject.h" +#include "rtl_constants.h" +#include "rtl_errors.h" +#include +#include +#include + +#include "erase_return.h" namespace rtl { @@ -53,6 +61,34 @@ namespace rtl } + template + FORCE_INLINE error Function::ecall_v(_args&& ...params) const noexcept + { + //m_functorIds[0].get_lambda_function<_args...>()->m_erasure->hop(std::forward<_args>(params)...); + const std::size_t argsId = detail::TypeId... >>::get(); + for (auto& functorId : m_functorIds) + { + if(argsId == functorId.m_lambda->m_functor.m_signatureId) [[likely]] + { + functorId.get_lambda_function<_args...>()->m_erasure->hop_v(std::forward<_args>(params)...); + break; + } + } + return error::None; + } + + + template + FORCE_INLINE std::any Function::ecall_r(_args&& ...params) const noexcept + { + auto functorId = getLambdaById(detail::TypeId... >>::get()); + if(functorId) { + return functorId->template get_lambda_function<_args...>()->m_erasure->hop_r(std::forward<_args>(params)...); + } + return std::any(); + } + + /* @method: hasSignatureId() @param: const std::size_t& (signatureId to be found) @return: the index of the functor in the functor-table. @@ -81,4 +117,15 @@ namespace rtl } return nullptr; } + + FORCE_INLINE const detail::FunctorId* Function::getLambdaById(const std::size_t pSignatureId) const + { + //simple linear-search, efficient for small set of elements. + for (const auto& functorId : m_functorIds) { + if (pSignatureId == functorId.m_lambda->m_functor.m_signatureId) [[likely]] { + return &functorId; + } + } + return nullptr; + } } diff --git a/ReflectionTemplateLib/rtl/rtl_typeid.h b/ReflectionTemplateLib/rtl/rtl_typeid.h index e898b588..8fe1d88e 100644 --- a/ReflectionTemplateLib/rtl/rtl_typeid.h +++ b/ReflectionTemplateLib/rtl/rtl_typeid.h @@ -15,6 +15,14 @@ #include #include +#if defined(_MSC_VER) +#define FORCE_INLINE __forceinline +#elif defined(__GNUC__) || defined(__clang__) +#define FORCE_INLINE inline __attribute__((always_inline)) +#else +#define FORCE_INLINE inline +#endif + namespace rtl { namespace detail @@ -38,7 +46,7 @@ namespace rtl { //'0' represents no type. [Never change, critical.] static constexpr const std::size_t None = 0; - static const std::size_t get() + FORCE_INLINE static std::size_t get() { if constexpr (!std::is_same_v<_type, std::nullptr_t>) { From 0312cd37bdacd919bb4c3d9bffc4d886f56b866d Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Sun, 28 Sep 2025 13:10:48 +0530 Subject: [PATCH 46/58] removed RTTI/virtual-funcs, wip. --- .../rtl/dispatch/lambda_function.h | 6 ------ .../rtl/dispatch/rtl_function.h | 6 +++--- .../rtl/dispatch/rtl_method.h | 6 +++--- .../rtl/erasure/erase_return.h | 19 ++++++++++++++----- ReflectionTemplateLib/rtl/erasure/erasure.h | 17 +++++++++++++++-- 5 files changed, 35 insertions(+), 19 deletions(-) diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 14a90ded..426239fb 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -48,11 +48,5 @@ namespace rtl::dispatch } return hopper_t(); } - - template - constexpr decltype(auto) operator()(args_t&&...params) const - { - return m_erasure->forward(std::forward(params)...); - } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h index 14ada51e..edcdea67 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h @@ -30,7 +30,7 @@ namespace rtl } template - [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept(noexcept_v) + [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept // (noexcept_v) { //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (*m_functor)(std::forward(params)...); @@ -53,8 +53,8 @@ namespace rtl template static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - template - static constexpr bool noexcept_v = noexcept(std::declval()(std::declval()...)); + //template + //static constexpr bool noexcept_v = noexcept(std::declval()(std::declval()...)); template friend struct dispatch::lambda_function; diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h index 27e9912c..4f60a560 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h @@ -33,7 +33,7 @@ namespace rtl } template - [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept(noexcept_v) + [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept //(noexcept_v) { static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (target.*m_functor)(std::forward(params)...); @@ -44,7 +44,7 @@ namespace rtl template static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - template - static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); + //template + //static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erase_return.h b/ReflectionTemplateLib/rtl/erasure/erase_return.h index 0f880333..571cfe8d 100644 --- a/ReflectionTemplateLib/rtl/erasure/erase_return.h +++ b/ReflectionTemplateLib/rtl/erasure/erase_return.h @@ -24,21 +24,30 @@ namespace rtl::erase { rtl::function m_function; - void hop_v(signature_ts&&...params) const noexcept override + function_return() + { + erasure_base::v_hop = vhop; + erasure_base::r_hop = rhop; + } + + FORCE_INLINE static void vhop(erasure_base* p_this, signature_ts&&...params) { if constexpr (std::is_void_v) { - m_function(std::forward(params)...); + auto this_p = static_cast*>(p_this); + this_p->m_function(std::forward(params)...); } } - std::any hop_r(signature_ts&&...params) const noexcept override + FORCE_INLINE static std::any rhop(erasure_base* p_this, signature_ts&&...params) { if constexpr (!std::is_void_v) { - return std::any(m_function(std::forward(params)...)); + auto this_p = static_cast*>(p_this); + auto&& ret_v = this_p->m_function(std::forward(params)...); + return std::any(std::forward(ret_v)); } else return std::any(); } }; - } \ No newline at end of file +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erasure.h b/ReflectionTemplateLib/rtl/erasure/erasure.h index 57cb6ea9..2f5a2b29 100644 --- a/ReflectionTemplateLib/rtl/erasure/erasure.h +++ b/ReflectionTemplateLib/rtl/erasure/erasure.h @@ -19,7 +19,20 @@ namespace rtl::erase template struct erasure_base { - virtual void hop_v(signature_ts&&...) const noexcept = 0; - virtual std::any hop_r(signature_ts&&...) const noexcept = 0; + using functor_vt = void(*)(erasure_base*, signature_ts&&...); + using functor_rt = std::any(*)(erasure_base*, signature_ts&&...); + + functor_vt v_hop = nullptr; + functor_rt r_hop = nullptr; + + FORCE_INLINE void hop_v(signature_ts&&...params) + { + v_hop(this, std::forward(params)...); + } + + FORCE_INLINE std::any hop_r(signature_ts&&...params) + { + return r_hop(this, std::forward(params)...); + } }; } \ No newline at end of file From dc0fff7f889c1baef188a23da054a4ed564fa35e Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Mon, 29 Sep 2025 12:02:16 +0530 Subject: [PATCH 47/58] return-erased basic integration done, method calls impl. --- .../src/ReflectedCallUnknownReturn.cpp | 17 +++--- .../MoveConstructorTests.cpp | 2 +- .../FunctionalityTests/StaticMethodTests.cpp | 4 +- .../rtl/builder/SetupMethod.hpp | 4 +- .../rtl/cache/cache_lambda_function.h | 8 +-- .../rtl/cache/cache_lambda_method.h | 13 +++- .../rtl/detail/inc/FunctionCaller.h | 6 ++ .../rtl/detail/inc/FunctionCaller.hpp | 26 ++++++++ .../rtl/detail/inc/MethodInvoker.h | 41 ++++++++++--- ReflectionTemplateLib/rtl/dispatch/functor.h | 2 +- .../rtl/dispatch/lambda_function.h | 8 +-- .../rtl/dispatch/lambda_method.h | 31 ++++++---- .../rtl/dispatch/rtl_const_method.h | 26 +++++--- .../rtl/dispatch/rtl_method.h | 19 +++++- .../rtl/erasure/CMakeLists.txt | 7 ++- .../erasure/{erasure.h => erase_function.h} | 10 ++- .../rtl/erasure/erase_method.h | 42 +++++++++++++ .../rtl/erasure/return_const_method.h | 61 +++++++++++++++++++ .../{erase_return.h => return_function.h} | 35 +++++++---- .../rtl/erasure/return_method.h | 61 +++++++++++++++++++ ReflectionTemplateLib/rtl/inc/Function.h | 6 -- ReflectionTemplateLib/rtl/inc/Function.hpp | 33 +--------- ReflectionTemplateLib/rtl/inc/Method.h | 13 ++-- ReflectionTemplateLib/rtl/rtl_forward_decls.h | 15 +++-- 24 files changed, 365 insertions(+), 125 deletions(-) rename ReflectionTemplateLib/rtl/erasure/{erasure.h => erase_function.h} (85%) create mode 100644 ReflectionTemplateLib/rtl/erasure/erase_method.h create mode 100644 ReflectionTemplateLib/rtl/erasure/return_const_method.h rename ReflectionTemplateLib/rtl/erasure/{erase_return.h => return_function.h} (59%) create mode 100644 ReflectionTemplateLib/rtl/erasure/return_method.h diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index 468afbb9..a4408980 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -138,7 +138,8 @@ void RtlFunction_call_ReturnUnknown::typeVoid(benchmark::State& state) static auto _ = _test0(); for (auto _ : state) { - benchmark::DoNotOptimize(SendMessage(bm::g_longStr)); + SendMessage.bind().call_v(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done); } } @@ -149,7 +150,7 @@ void RtlFunction_call_ReturnUnknown::typeNonVoid(benchmark::State& state) static auto _ = _test2(); for (auto _ : state) { - benchmark::DoNotOptimize(GetMessage(bm::g_longStr)); + benchmark::DoNotOptimize(GetMessage.bind().call_r(bm::g_longStr)); } } @@ -157,12 +158,11 @@ void RtlFunction_call_ReturnUnknown::typeNonVoid(benchmark::State& state) void RtlFunction_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) { static auto _ = _test1(); + static bm::Node node; for (auto _ : state) { - //Testings: - SendMessage.ecall_v(bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done->c_str()); - //benchmark::DoNotOptimize(NodeSendMessage(nodeObj)(bm::g_longStr)); + NodeSendMessage(node).call_v(bm::g_longStr); + benchmark::DoNotOptimize(bm::g_work_done); } } @@ -170,10 +170,9 @@ void RtlFunction_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) void RtlFunction_callMethod_ReturnUnknown::typeNonVoid(benchmark::State& state) { static auto _ = _test3(); + static bm::Node node; for (auto _ : state) { - //Testing: - benchmark::DoNotOptimize(GetMessage.ecall_r(bm::g_longStr)); - //benchmark::DoNotOptimize(NodeGetMessage(nodeObj)(bm::g_longStr)); + benchmark::DoNotOptimize(NodeGetMessage(node).call_r(bm::g_longStr)); } } \ No newline at end of file diff --git a/RTLTestRunApp/src/FunctionalityTests/MoveConstructorTests.cpp b/RTLTestRunApp/src/FunctionalityTests/MoveConstructorTests.cpp index d4c07bc0..02431be3 100644 --- a/RTLTestRunApp/src/FunctionalityTests/MoveConstructorTests.cpp +++ b/RTLTestRunApp/src/FunctionalityTests/MoveConstructorTests.cpp @@ -228,7 +228,7 @@ namespace rtl_tests // Calender::create is a static method that returns stack-allocated Calender object. // Calling this via reflection, moves the return value from Calender::create to here. - auto [err0, calender0] = (*createCalender)()(); + auto [err0, calender0] = createCalender->bind().call(); EXPECT_TRUE(err0 == error::None); ASSERT_FALSE(calender0.isEmpty()); diff --git a/RTLTestRunApp/src/FunctionalityTests/StaticMethodTests.cpp b/RTLTestRunApp/src/FunctionalityTests/StaticMethodTests.cpp index 5d93608f..f8a80759 100644 --- a/RTLTestRunApp/src/FunctionalityTests/StaticMethodTests.cpp +++ b/RTLTestRunApp/src/FunctionalityTests/StaticMethodTests.cpp @@ -21,7 +21,7 @@ namespace rtl_tests ASSERT_TRUE(getDefaults); EXPECT_TRUE(getDefaults->hasSignature<>()); //empty template params checks for zero arguments. - auto [err, ret] = (*getDefaults)()(); + auto [err, ret] = getDefaults->bind().call(); EXPECT_TRUE(err == error::None); ASSERT_FALSE(ret.isEmpty()); EXPECT_TRUE(ret.canViewAs()); @@ -59,7 +59,7 @@ namespace rtl_tests ASSERT_TRUE(getProfile); EXPECT_TRUE(getProfile->hasSignature()); { - auto [err, ret] = (*getProfile)()(true); + auto [err, ret] = getProfile->bind().call(true); EXPECT_TRUE(err == error::None); ASSERT_FALSE(ret.isEmpty()); EXPECT_TRUE(ret.canViewAs()); diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 08c1e9d2..69661226 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -170,7 +170,7 @@ namespace rtl::detail const dispatch::lambda_base* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = cache::lambda_method<_recordType, _signature...>::instance(); + auto& lambdaCache = cache::lambda_method<_recordType, _returnType, _signature...>::instance(); auto& functorCache = cache::method_ptr<_recordType, _returnType, _signature...>::instance(); auto& functor = functorCache.push(pFunctor, pIndex); @@ -241,7 +241,7 @@ namespace rtl::detail const dispatch::lambda_base* lambdaPtr = nullptr; const auto& updateIndex = [&](std::size_t pIndex)-> void { - auto& lambdaCache = cache::lambda_method<_recordType, _signature...>::instance(); + auto& lambdaCache = cache::lambda_method<_recordType, _returnType, _signature...>::instance(); auto& functorCache = cache::method_ptr::instance(); auto& functor = functorCache.push(pFunctor, pIndex); diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h index a83566e0..6318614f 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h @@ -14,7 +14,7 @@ #include #include "lambda_function.h" -#include "erase_return.h" +#include "return_function.h" namespace rtl::cache { @@ -29,8 +29,8 @@ namespace rtl::cache const dispatch::lambda_function& push(const dispatch::functor& fptr) const { - m_erasure_cache.push_back(erase::function_return()); - erase::erasure_base* erasure = &m_erasure_cache.back(); + m_erasure_cache.push_back(erase::return_function()); + erase::function* erasure = &m_erasure_cache.back(); m_cache.push_back(dispatch::lambda_function(fptr, erasure)); fptr.m_lambda = &m_cache.back(); @@ -48,7 +48,7 @@ namespace rtl::cache // No reallocation occurs; original objects stay intact mutable std::list> m_cache; - mutable std::list> m_erasure_cache; + mutable std::list> m_erasure_cache; lambda_function() = default; }; diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h index f096814d..28a6c235 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h @@ -14,10 +14,12 @@ #include #include "lambda_method.h" +#include "return_method.h" +#include "return_const_method.h" namespace rtl::cache { - template + template struct lambda_method { static const lambda_method& instance() @@ -28,8 +30,14 @@ namespace rtl::cache const dispatch::lambda_method& push(const dispatch::functor& fptr) const { - m_cache.push_back(dispatch::lambda_method(fptr)); + m_erasure_cache.push_back(erase::return_method()); + erase::method* erasure = &m_erasure_cache.back(); + + m_cache.push_back(dispatch::lambda_method(fptr, erasure)); fptr.m_lambda = &m_cache.back(); + + (m_cache.back()).template init_erasure(); + return m_cache.back(); } @@ -42,6 +50,7 @@ namespace rtl::cache // No reallocation occurs; original objects stay intact mutable std::list> m_cache; + mutable std::list> m_erasure_cache; lambda_method() = default; }; diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h index 957c8c00..f4e1fd65 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h @@ -30,6 +30,12 @@ namespace rtl::detail template constexpr rtl::Return operator()(_args&&...params) const noexcept; + template + rtl::error call_v(_args&&...) const noexcept; + + template + std::any call_r(_args&&...) const noexcept; + friend Function; }; } diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index af125bd2..5ce082e0 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -16,6 +16,8 @@ #include "FunctionCaller.h" #include "FunctorContainer.h" +#include "erase_function.h" + namespace rtl::detail { template @@ -40,6 +42,30 @@ namespace rtl::detail { return call(std::forward<_args>(params)...); } + + + template + template + FORCE_INLINE error FunctionCaller<_signature...>::call_v(_args&& ...params) const noexcept + { + auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); + if (functorId) [[likely]] { + functorId->template get_lambda_function<_args...>()->m_erasure->hop_v(std::forward<_args>(params)...); + } + return error::None; + } + + + template + template + FORCE_INLINE std::any FunctionCaller<_signature...>::call_r(_args&& ...params) const noexcept + { + auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); + if (functorId) [[likely]] { + return functorId->template get_lambda_function<_args...>()->m_erasure->hop_r(std::forward<_args>(params)...); + } + return std::any(); + } } diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h index 38ba7f74..0e32e36f 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h @@ -11,7 +11,38 @@ #pragma once -#include "rtl_forward_decls.h" +#include "erase_method.h" + +namespace rtl::detail +{ + template + struct ErasedInvoker + { + const Method& m_method; + + const _recordType& m_target; + + template + constexpr error call_v(_args&&...params) const noexcept + { + auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); + if (functorId) [[likely]] { + functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->hop_v(m_target, std::forward<_args>(params)...); + } + return error::None; + } + + template + constexpr std::any call_r(_args&&...params) const noexcept + { + auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); + if (functorId) [[likely]] { + return functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->hop_r(m_target, std::forward<_args>(params)...); + } + return std::any(); + } + }; +} namespace rtl::detail { @@ -32,8 +63,6 @@ namespace rtl::detail { static Return invoke(const Method& pMethod, const RObject& pTarget, _args&&...); }; - public: - template Return call(_args&&...) const noexcept; @@ -41,8 +70,6 @@ namespace rtl::detail { constexpr Return operator()(_args&&...params) const noexcept { return call(std::forward<_args>(params)...); } - - friend Method; }; @@ -62,8 +89,6 @@ namespace rtl::detail { static Return invoke(const Method& pMethod, const RObject& pTarget, _args&&...); }; - public: - template Return call(_args&&...) const noexcept; @@ -71,8 +96,6 @@ namespace rtl::detail { constexpr Return operator()(_args&&...params) const noexcept { return call(std::forward<_args>(params)...); } - - friend Method; }; } diff --git a/ReflectionTemplateLib/rtl/dispatch/functor.h b/ReflectionTemplateLib/rtl/dispatch/functor.h index 070c4a59..e079761d 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor.h @@ -40,7 +40,7 @@ namespace rtl::dispatch template friend struct cache::lambda_function; - template + template friend struct cache::lambda_method; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 426239fb..efd7d7df 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -14,7 +14,7 @@ #include "lambda.h" #include "function_ptr.h" #include "rtl_function.h" -#include "erase_return.h" +#include "return_function.h" namespace rtl::dispatch { @@ -24,9 +24,9 @@ namespace rtl::dispatch template using hopper_t = rtl::function; - erase::erasure_base* m_erasure; + erase::function* m_erasure; - lambda_function(const functor& p_functor, erase::erasure_base* p_erasure) noexcept + lambda_function(const functor& p_functor, erase::function* p_erasure) noexcept : lambda_base(p_functor) , m_erasure(p_erasure) { } @@ -34,7 +34,7 @@ namespace rtl::dispatch template constexpr void init_erasure() const { - auto erasure = static_cast*>(m_erasure); + auto erasure = static_cast*>(m_erasure); erasure->m_function = get_hopper(); } diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index b7b24fb5..cfc3d954 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -15,6 +15,9 @@ #include "method_ptr.h" #include "rtl_method.h" #include "rtl_const_method.h" +#include "return_method.h" +#include "return_const_method.h" + namespace rtl::dispatch { @@ -22,37 +25,43 @@ namespace rtl::dispatch struct lambda_method : public lambda_base { template - using hopper_t = method; + using hopper_t = rtl::method; template - using hopper_ct = method; + using hopper_ct = rtl::method; + + erase::method* m_erasure; - lambda_method(const functor& p_functor) noexcept - :lambda_base(p_functor) + lambda_method(const functor& p_functor, erase::method* p_erasure) noexcept + : lambda_base(p_functor) + , m_erasure(p_erasure) { } + template + constexpr void init_erasure() const + { + auto erasure = static_cast*>(m_erasure); + erasure->m_method = get_hopper(); + } template requires (std::is_const_v == false) constexpr const hopper_t get_hopper(std::size_t p_returnId = 0) const { if (p_returnId == 0 || p_returnId == m_functor.m_returnId) [[likely]] { - return hopper_t { - static_cast&>(m_functor).f_ptr() - }; + auto fptr = static_cast&>(m_functor).f_ptr(); + return hopper_t(fptr); } return hopper_t(); } - template requires (std::is_const_v == true) constexpr const hopper_ct get_hopper(std::size_t p_returnId = 0) const { if (p_returnId == 0 || p_returnId == m_functor.m_returnId) [[likely]] { - return hopper_ct { - static_cast&>(m_functor).f_ptr() - }; + auto fptr = static_cast&>(m_functor).f_ptr(); + return hopper_ct(fptr); } return hopper_ct(); } diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_const_method.h b/ReflectionTemplateLib/rtl/dispatch/rtl_const_method.h index 62da2180..5b4edf73 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_const_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_const_method.h @@ -18,11 +18,9 @@ namespace rtl { template - struct method + struct method { - using fptr_t = return_t(record_t::*)(signature_ts...) const; - - const fptr_t m_functor = nullptr; + using fptr_t = return_t (record_t::*)(signature_ts...) const; constexpr auto f_ptr() const { return m_functor; @@ -33,18 +31,30 @@ namespace rtl } template - [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept(noexcept_v) + [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept//(noexcept_v) { - static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (target.*m_functor)(std::forward(params)...); } + method(fptr_t p_functor) : m_functor(p_functor) + { } + + method() = default; + method(method&&) = default; + method(const method&) = default; + + method& operator=(method&&) = default; + method& operator=(const method&) = default; + private: + fptr_t m_functor = nullptr; + template static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - template - static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); + //template + //static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h index 4f60a560..8154e69b 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h @@ -22,8 +22,6 @@ namespace rtl { using fptr_t = return_t (record_t::*)(signature_ts...); - const fptr_t m_functor = nullptr; - constexpr auto f_ptr() const { return m_functor; } @@ -35,16 +33,31 @@ namespace rtl template [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept //(noexcept_v) { - static_assert(is_args_t_ok, "Argument types don't match the expected signature."); + //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (target.*m_functor)(std::forward(params)...); } + method(fptr_t p_functor) : m_functor(p_functor) + { } + + method() = default; + method(method&&) = default; + method(const method&) = default; + + method& operator=(method&&) = default; + method& operator=(const method&) = default; + private: + fptr_t m_functor = nullptr; + template static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; //template //static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); + + template + friend struct dispatch::lambda_method; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt b/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt index 03494399..da69ba9b 100644 --- a/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt @@ -2,8 +2,11 @@ # Collect headers in this folder (absolute paths) set(LOCAL_HEADERS - "${CMAKE_CURRENT_SOURCE_DIR}/erasure.h" - "${CMAKE_CURRENT_SOURCE_DIR}/erase_return.h" + "${CMAKE_CURRENT_SOURCE_DIR}/erase_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/erase_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/return_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/return_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/return_const_method.h" ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/erasure/erasure.h b/ReflectionTemplateLib/rtl/erasure/erase_function.h similarity index 85% rename from ReflectionTemplateLib/rtl/erasure/erasure.h rename to ReflectionTemplateLib/rtl/erasure/erase_function.h index 2f5a2b29..dd6012be 100644 --- a/ReflectionTemplateLib/rtl/erasure/erasure.h +++ b/ReflectionTemplateLib/rtl/erasure/erase_function.h @@ -17,12 +17,16 @@ namespace rtl::erase { template - struct erasure_base + struct function { - using functor_vt = void(*)(erasure_base*, signature_ts&&...); - using functor_rt = std::any(*)(erasure_base*, signature_ts&&...); + using this_t = function; + + using functor_vt = void(*)(this_t*, signature_ts&&...); + + using functor_rt = std::any(*)(this_t*, signature_ts&&...); functor_vt v_hop = nullptr; + functor_rt r_hop = nullptr; FORCE_INLINE void hop_v(signature_ts&&...params) diff --git a/ReflectionTemplateLib/rtl/erasure/erase_method.h b/ReflectionTemplateLib/rtl/erasure/erase_method.h new file mode 100644 index 00000000..a90ffbf7 --- /dev/null +++ b/ReflectionTemplateLib/rtl/erasure/erase_method.h @@ -0,0 +1,42 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include +#include "rtl_forward_decls.h" + +namespace rtl::erase +{ + template + struct method + { + using this_t = method; + + using functor_vt = void(*)(this_t*, const record_t&, signature_ts&&...); + + using functor_rt = std::any(*)(this_t*, const record_t&, signature_ts&&...); + + functor_vt v_hop = nullptr; + + functor_rt r_hop = nullptr; + + FORCE_INLINE void hop_v(const record_t& p_target, signature_ts&&...params) + { + v_hop(this, p_target, std::forward(params)...); + } + + FORCE_INLINE std::any hop_r(const record_t& p_target, signature_ts&&...params) + { + return r_hop(this, p_target, std::forward(params)...); + } + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/return_const_method.h b/ReflectionTemplateLib/rtl/erasure/return_const_method.h new file mode 100644 index 00000000..a47f8521 --- /dev/null +++ b/ReflectionTemplateLib/rtl/erasure/return_const_method.h @@ -0,0 +1,61 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "erase_method.h" + +namespace rtl::erase +{ + template + struct return_method : public method + { + using base_t = method; + + using this_t = return_method; + + rtl::method m_method; + + return_method() + { + base_t::v_hop = hop_v; + base_t::r_hop = hop_r; + } + + FORCE_INLINE static void hop_v(base_t* p_this, const record_t& p_target, signature_ts&&...params) + { + if constexpr (std::is_void_v) + { + auto this_p = static_cast(p_this); + this_p->m_method(p_target, std::forward(params)...); + } + } + + FORCE_INLINE static std::any hop_r(base_t* p_this, const record_t& p_target, signature_ts&&...params) + { + if constexpr (!std::is_void_v) + { + auto this_p = static_cast(p_this); + auto&& ret_v = this_p->m_method(p_target, std::forward(params)...); + + if constexpr (std::is_reference_v) + { + return std::any(&ret_v); + } + else + { + return std::any(std::forward(ret_v)); + } + } + else return std::any(); + } + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erase_return.h b/ReflectionTemplateLib/rtl/erasure/return_function.h similarity index 59% rename from ReflectionTemplateLib/rtl/erasure/erase_return.h rename to ReflectionTemplateLib/rtl/erasure/return_function.h index 571cfe8d..54b2d1e0 100644 --- a/ReflectionTemplateLib/rtl/erasure/erase_return.h +++ b/ReflectionTemplateLib/rtl/erasure/return_function.h @@ -11,41 +11,50 @@ #pragma once -#include "erasure.h" -#include "rtl_traits.h" +#include "erase_function.h" #include "rtl_function.h" -#include "rtl_errors.h" -#include namespace rtl::erase { template - struct function_return : public erasure_base + struct return_function : public function { + using base_t = function; + + using this_t = return_function; + rtl::function m_function; - function_return() + return_function() { - erasure_base::v_hop = vhop; - erasure_base::r_hop = rhop; + base_t::v_hop = hop_v; + base_t::r_hop = hop_r; } - FORCE_INLINE static void vhop(erasure_base* p_this, signature_ts&&...params) + FORCE_INLINE static void hop_v(base_t* p_this, signature_ts&&...params) { if constexpr (std::is_void_v) { - auto this_p = static_cast*>(p_this); + auto this_p = static_cast(p_this); this_p->m_function(std::forward(params)...); } } - FORCE_INLINE static std::any rhop(erasure_base* p_this, signature_ts&&...params) + FORCE_INLINE static std::any hop_r(base_t* p_this, signature_ts&&...params) { if constexpr (!std::is_void_v) { - auto this_p = static_cast*>(p_this); + auto this_p = static_cast(p_this); auto&& ret_v = this_p->m_function(std::forward(params)...); - return std::any(std::forward(ret_v)); + + if constexpr (std::is_reference_v) + { + return std::any(&ret_v); + } + else + { + return std::any(std::forward(ret_v)); + } } else return std::any(); } diff --git a/ReflectionTemplateLib/rtl/erasure/return_method.h b/ReflectionTemplateLib/rtl/erasure/return_method.h new file mode 100644 index 00000000..3129c06f --- /dev/null +++ b/ReflectionTemplateLib/rtl/erasure/return_method.h @@ -0,0 +1,61 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "erase_method.h" + +namespace rtl::erase +{ + template + struct return_method : public method + { + using base_t = method; + + using this_t = return_method; + + rtl::method m_method; + + return_method() + { + base_t::v_hop = hop_v; + base_t::r_hop = hop_r; + } + + FORCE_INLINE static void hop_v(base_t* p_this, const record_t& p_target, signature_ts&&...params) + { + if constexpr (std::is_void_v) + { + auto this_p = static_cast(p_this); + this_p->m_method(const_cast(p_target), std::forward(params)...); + } + } + + FORCE_INLINE static std::any hop_r(base_t* p_this, const record_t& p_target, signature_ts&&...params) + { + if constexpr (!std::is_void_v) + { + auto this_p = static_cast(p_this); + auto&& ret_v = this_p->m_method(const_cast(p_target), std::forward(params)...); + + if constexpr (std::is_reference_v) + { + return std::any(&ret_v); + } + else + { + return std::any(std::forward(ret_v)); + } + } + else return std::any(); + } + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index a08aade2..97822e37 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -107,12 +107,6 @@ namespace rtl { template constexpr const detail::FunctionCaller<_signature...> bind() const noexcept; - template - rtl::error ecall_v(_args&&...) const noexcept; - - template - std::any ecall_r(_args&&...) const noexcept; - friend detail::CxxReflection; friend detail::ReflectionBuilder; diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index 49a531d5..ebc2d6f8 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -16,11 +16,7 @@ #include "RObject.h" #include "rtl_constants.h" #include "rtl_errors.h" -#include -#include -#include -#include "erase_return.h" namespace rtl { @@ -61,34 +57,6 @@ namespace rtl } - template - FORCE_INLINE error Function::ecall_v(_args&& ...params) const noexcept - { - //m_functorIds[0].get_lambda_function<_args...>()->m_erasure->hop(std::forward<_args>(params)...); - const std::size_t argsId = detail::TypeId... >>::get(); - for (auto& functorId : m_functorIds) - { - if(argsId == functorId.m_lambda->m_functor.m_signatureId) [[likely]] - { - functorId.get_lambda_function<_args...>()->m_erasure->hop_v(std::forward<_args>(params)...); - break; - } - } - return error::None; - } - - - template - FORCE_INLINE std::any Function::ecall_r(_args&& ...params) const noexcept - { - auto functorId = getLambdaById(detail::TypeId... >>::get()); - if(functorId) { - return functorId->template get_lambda_function<_args...>()->m_erasure->hop_r(std::forward<_args>(params)...); - } - return std::any(); - } - - /* @method: hasSignatureId() @param: const std::size_t& (signatureId to be found) @return: the index of the functor in the functor-table. @@ -118,6 +86,7 @@ namespace rtl return nullptr; } + FORCE_INLINE const detail::FunctorId* Function::getLambdaById(const std::size_t pSignatureId) const { //simple linear-search, efficient for small set of elements. diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index 18cf1ea3..f4249ca5 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -69,14 +69,10 @@ namespace rtl { template const detail::NonConstInvoker<_signature...> bind(constCast&& pTarget) const; - /* @method: operator()() - @return: lambda - * accepts no arguments for 'target', since associated functor is static-member-functions. - * returns a lambda, which forwards the call to finally call the associated static-member-function functor. - * provides syntax like,'method()(params...)', first'()' is empty & second'()' takes the actual params. - */ constexpr auto operator()() const + template + constexpr detail::ErasedInvoker<_recordType> operator()(const _recordType& pTarget) const { - return detail::FunctionCaller<>{ this }; + return detail::ErasedInvoker<_recordType>{ (*this), pTarget }; } @@ -105,5 +101,8 @@ namespace rtl { template friend struct detail::NonConstInvoker; + + template + friend struct detail::ErasedInvoker; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/rtl_forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h index 36e30570..5d5c391e 100644 --- a/ReflectionTemplateLib/rtl/rtl_forward_decls.h +++ b/ReflectionTemplateLib/rtl/rtl_forward_decls.h @@ -34,13 +34,16 @@ namespace rtl namespace erase { template - struct erasure_base; - - template struct function; - template - struct method; + template + struct method; + + template + struct return_function; + + template + struct return_method; } namespace detail @@ -62,7 +65,7 @@ namespace rtl template struct lambda_function; - template + template struct lambda_method; } From 7eb3dd6f38b3b48dfa5f97dbc88177f9b08b7742 Mon Sep 17 00:00:00 2001 From: neeraj Date: Mon, 29 Sep 2025 12:26:12 +0530 Subject: [PATCH 48/58] gcc/clang compile error fix. --- .../src/ReflectedCallUnknownReturn.cpp | 2 +- .../rtl/detail/inc/FunctionCaller.h | 6 +---- .../rtl/detail/inc/FunctionCaller.hpp | 2 +- .../rtl/detail/inc/MethodInvoker.h | 20 +++----------- .../rtl/detail/inc/MethodInvoker.hpp | 26 +++++++++++++++++++ .../rtl/dispatch/rtl_function.h | 3 --- .../rtl/dispatch/rtl_method.h | 3 --- 7 files changed, 32 insertions(+), 30 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index a4408980..3c65fee9 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -162,7 +162,7 @@ void RtlFunction_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) for (auto _ : state) { NodeSendMessage(node).call_v(bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done); + benchmark::DoNotOptimize(bm::g_work_done->c_str()); } } diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h index f4e1fd65..2ec2e6c2 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h @@ -22,8 +22,6 @@ namespace rtl::detail { const Function* m_function; - public: - template rtl::Return call(_args&&...) const noexcept; @@ -31,12 +29,10 @@ namespace rtl::detail constexpr rtl::Return operator()(_args&&...params) const noexcept; template - rtl::error call_v(_args&&...) const noexcept; + constexpr rtl::error call_v(_args&&...) const noexcept; template std::any call_r(_args&&...) const noexcept; - - friend Function; }; } diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index 5ce082e0..491a9c89 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -46,7 +46,7 @@ namespace rtl::detail template template - FORCE_INLINE error FunctionCaller<_signature...>::call_v(_args&& ...params) const noexcept + constexpr error FunctionCaller<_signature...>::call_v(_args&& ...params) const noexcept { auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h index 0e32e36f..02cc947b 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h @@ -13,7 +13,7 @@ #include "erase_method.h" -namespace rtl::detail +namespace rtl::detail { template struct ErasedInvoker @@ -23,24 +23,10 @@ namespace rtl::detail const _recordType& m_target; template - constexpr error call_v(_args&&...params) const noexcept - { - auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); - if (functorId) [[likely]] { - functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->hop_v(m_target, std::forward<_args>(params)...); - } - return error::None; - } + constexpr error call_v(_args&&...params) const noexcept; template - constexpr std::any call_r(_args&&...params) const noexcept - { - auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); - if (functorId) [[likely]] { - return functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->hop_r(m_target, std::forward<_args>(params)...); - } - return std::any(); - } + std::any call_r(_args&&...params) const noexcept; }; } diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index 6f7d9074..c8e6d4ee 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -180,4 +180,30 @@ namespace rtl::detail } return method<_returnType(_recordType::*)(_signature...)>(); } +} + + +namespace rtl::detail +{ + template + template + constexpr error ErasedInvoker<_recordType>::call_v(_args&&...params) const noexcept + { + auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); + if (functorId) [[likely]] { + functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->hop_v(m_target, std::forward<_args>(params)...); + } + return error::None; + } + + template + template + FORCE_INLINE std::any ErasedInvoker<_recordType>::call_r(_args&&...params) const noexcept + { + auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); + if (functorId) [[likely]] { + return functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->hop_r(m_target, std::forward<_args>(params)...); + } + return std::any(); + } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h index edcdea67..f08071de 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h @@ -55,8 +55,5 @@ namespace rtl //template //static constexpr bool noexcept_v = noexcept(std::declval()(std::declval()...)); - - template - friend struct dispatch::lambda_function; }; } diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h index 8154e69b..0f60353a 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h @@ -56,8 +56,5 @@ namespace rtl //template //static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); - - template - friend struct dispatch::lambda_method; }; } \ No newline at end of file From 5a81261124603bdd3915a30c5694562c4f60bd00 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Mon, 29 Sep 2025 20:42:10 +0530 Subject: [PATCH 49/58] general refactor, restructure, renames. --- .../src/ReflectedCallKnownReturn.cpp | 4 +-- .../src/ReflectedCallUnknownReturn.cpp | 4 +-- .../rtl/builder/FunctorContainer.h | 4 +-- .../rtl/builder/MethodContainer.h | 6 ++-- .../rtl/builder/RObjectBuilder.hpp | 6 ++-- .../rtl/builder/SetupMethod.hpp | 2 +- .../rtl/cache/CMakeLists.txt | 5 ++-- .../rtl/cache/cache_function_ptr.h | 2 +- .../rtl/cache/cache_lambda_function.h | 16 +++++----- .../rtl/cache/cache_lambda_method.h | 18 +++++------ .../rtl/cache/cache_method_ptr.h | 2 +- ..._method_ptr.h => cache_method_ptr_const.h} | 2 +- .../rtl/detail/inc/CallReflector.h | 8 ++--- .../rtl/detail/inc/FunctionCaller.hpp | 10 +++---- .../rtl/detail/inc/MethodInvoker.h | 2 +- .../rtl/detail/inc/MethodInvoker.hpp | 14 ++++----- .../rtl/detail/inc/RObjExtracter.h | 10 +++---- .../rtl/detail/inc/RObjectId.h | 4 +-- .../rtl/dispatch/CMakeLists.txt | 11 +++---- .../{function_ptr.h => functor_function.h} | 0 .../{method_ptr.h => functor_method.h} | 0 ...st_method_ptr.h => functor_method_const.h} | 0 .../rtl/dispatch/lambda_function.h | 15 +++------- .../rtl/dispatch/lambda_method.h | 18 ++++------- ...{rtl_const_method.h => rtl_method_const.h} | 0 .../rtl/erasure/CMakeLists.txt | 12 ++++---- .../{return_function.h => aware_function.h} | 30 +++++++++---------- .../{return_method.h => aware_method.h} | 28 ++++++++--------- ...rn_const_method.h => aware_method_const.h} | 28 ++++++++--------- .../{erase_function.h => erased_function.h} | 30 ++++++++++--------- .../{erase_method.h => erased_method.h} | 30 ++++++++++--------- ReflectionTemplateLib/rtl/inc/Function.hpp | 6 ++-- ReflectionTemplateLib/rtl/inc/Method.hpp | 4 +-- ReflectionTemplateLib/rtl/inc/RObject.hpp | 8 ++--- ReflectionTemplateLib/rtl/rtl_constants.h | 6 ++-- ReflectionTemplateLib/rtl/rtl_errors.h | 2 +- ReflectionTemplateLib/rtl/rtl_forward_decls.h | 8 ++--- ReflectionTemplateLib/rtl/rtl_typeid.h | 8 ++--- 38 files changed, 175 insertions(+), 188 deletions(-) rename ReflectionTemplateLib/rtl/cache/{cache_const_method_ptr.h => cache_method_ptr_const.h} (98%) rename ReflectionTemplateLib/rtl/dispatch/{function_ptr.h => functor_function.h} (100%) rename ReflectionTemplateLib/rtl/dispatch/{method_ptr.h => functor_method.h} (100%) rename ReflectionTemplateLib/rtl/dispatch/{const_method_ptr.h => functor_method_const.h} (100%) rename ReflectionTemplateLib/rtl/dispatch/{rtl_const_method.h => rtl_method_const.h} (100%) rename ReflectionTemplateLib/rtl/erasure/{return_function.h => aware_function.h} (66%) rename ReflectionTemplateLib/rtl/erasure/{return_method.h => aware_method.h} (65%) rename ReflectionTemplateLib/rtl/erasure/{return_const_method.h => aware_method_const.h} (63%) rename ReflectionTemplateLib/rtl/erasure/{erase_function.h => erased_function.h} (57%) rename ReflectionTemplateLib/rtl/erasure/{erase_method.h => erased_method.h} (54%) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 7dd43790..f03456ba 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -25,7 +25,7 @@ namespace std::optional function = cxx::mirror().getFunction("getMessage"); if(!function) { - std::cerr << "[00] error: function 'getMessage' not found."; + std::cerr << "[00] error: erase_function 'getMessage' not found."; std::abort(); } return function->lambda().argsT().returnT(); @@ -36,7 +36,7 @@ namespace std::optional function = cxx::mirror().getFunction("sendMessage"); if(!function) { - std::cerr << "[01] error: function 'sendMessage' not found."; + std::cerr << "[01] error: erase_function 'sendMessage' not found."; std::abort(); } return function->lambda().argsT().returnT(); diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index 3c65fee9..81e287b1 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -21,7 +21,7 @@ namespace { std::optional function = cxx::mirror().getFunction("getMessage"); if (!function) { - std::cerr << "[0] error: function 'getMessage' not found.\n"; + std::cerr << "[0] error: erase_function 'getMessage' not found.\n"; std::abort(); } return *function; @@ -31,7 +31,7 @@ namespace { std::optional function = cxx::mirror().getFunction("sendMessage"); if (!function) { - std::cerr << "[1] error: function 'sendMessage' not found.\n"; + std::cerr << "[1] error: erase_function 'sendMessage' not found.\n"; std::abort(); } return *function; diff --git a/ReflectionTemplateLib/rtl/builder/FunctorContainer.h b/ReflectionTemplateLib/rtl/builder/FunctorContainer.h index 31c1e82f..f2109e41 100644 --- a/ReflectionTemplateLib/rtl/builder/FunctorContainer.h +++ b/ReflectionTemplateLib/rtl/builder/FunctorContainer.h @@ -41,13 +41,13 @@ namespace rtl { public: //every FunctorContainer<...> will have a unique-id. - FORCE_INLINE static std::size_t getContainerId() { + ForceInline static std::size_t getContainerId() { static const std::size_t containerId = generate_unique_id(); return containerId; } //get the vector holding lambdas as 'const-ref' - FORCE_INLINE const static std::vector& getOverloads() { + ForceInline const static std::vector& getOverloads() { static std::vector& functorTable = getFunctorTable(); return functorTable; } diff --git a/ReflectionTemplateLib/rtl/builder/MethodContainer.h b/ReflectionTemplateLib/rtl/builder/MethodContainer.h index 0a84ffd6..a542b033 100644 --- a/ReflectionTemplateLib/rtl/builder/MethodContainer.h +++ b/ReflectionTemplateLib/rtl/builder/MethodContainer.h @@ -52,7 +52,7 @@ namespace rtl { } //get the vector holding lambdas as 'const-ref' - FORCE_INLINE static const std::vector& getMethodFunctors() { + ForceInline static const std::vector& getMethodFunctors() { static std::vector& functorTable = getFunctorTable(); return functorTable; } @@ -118,14 +118,14 @@ namespace rtl { public: //every MethodContainer will have a unique-id. - FORCE_INLINE static std::size_t getContainerId() { + ForceInline static std::size_t getContainerId() { //holds unique-id static const std::size_t containerId = generate_unique_id(); return containerId; } //get the vector holding lambdas as 'const-ref' - FORCE_INLINE static const std::vector& getMethodFunctors() { + ForceInline static const std::vector& getMethodFunctors() { static std::vector& functorTable = getFunctorTable(); return functorTable; } diff --git a/ReflectionTemplateLib/rtl/builder/RObjectBuilder.hpp b/ReflectionTemplateLib/rtl/builder/RObjectBuilder.hpp index ded14dad..1504f405 100644 --- a/ReflectionTemplateLib/rtl/builder/RObjectBuilder.hpp +++ b/ReflectionTemplateLib/rtl/builder/RObjectBuilder.hpp @@ -20,7 +20,7 @@ namespace rtl::detail { template - FORCE_INLINE const std::vector& getConverters() noexcept + ForceInline const std::vector& getConverters() noexcept { // extract wrapper info. using _W = traits::std_wrapper>; @@ -32,7 +32,7 @@ namespace rtl::detail template template requires (_allocOn == alloc::Heap) - FORCE_INLINE RObject RObjectBuilder::build(T&& pVal, std::optional pClonerId, bool pIsConstCastSafe) noexcept + ForceInline RObject RObjectBuilder::build(T&& pVal, std::optional pClonerId, bool pIsConstCastSafe) noexcept { using _T = traits::raw_t; return RObject( std::any{ @@ -46,7 +46,7 @@ namespace rtl::detail template template requires (_allocOn == alloc::Stack) - FORCE_INLINE RObject RObjectBuilder::build(T&& pVal, std::optional pClonerId, bool pIsConstCastSafe) noexcept + ForceInline RObject RObjectBuilder::build(T&& pVal, std::optional pClonerId, bool pIsConstCastSafe) noexcept { using _T = traits::raw_t; constexpr bool isRawPointer = std::is_pointer_v>; diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 69661226..2957d82b 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -20,7 +20,7 @@ #include "lambda_method.h" #include "cache_method_ptr.h" -#include "cache_const_method_ptr.h" +#include "cache_method_ptr_const.h" #include "cache_lambda_method.h" namespace rtl::detail diff --git a/ReflectionTemplateLib/rtl/cache/CMakeLists.txt b/ReflectionTemplateLib/rtl/cache/CMakeLists.txt index 4e5af74d..b301f6a4 100644 --- a/ReflectionTemplateLib/rtl/cache/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/cache/CMakeLists.txt @@ -4,9 +4,10 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/cache_lambda_method.h" "${CMAKE_CURRENT_SOURCE_DIR}/cache_lambda_function.h" - "${CMAKE_CURRENT_SOURCE_DIR}/cache_function_ptr.h" + "${CMAKE_CURRENT_SOURCE_DIR}/cache_method_ptr.h" - "${CMAKE_CURRENT_SOURCE_DIR}/cache_const_method_ptr.h" + "${CMAKE_CURRENT_SOURCE_DIR}/cache_function_ptr.h" + "${CMAKE_CURRENT_SOURCE_DIR}/cache_method_ptr_const.h" ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h index 34c40f4b..fd012ac2 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_function_ptr.h @@ -13,7 +13,7 @@ #include -#include "function_ptr.h" +#include "functor_function.h" namespace rtl::cache { diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h index 6318614f..4e3095fc 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h @@ -14,7 +14,7 @@ #include #include "lambda_function.h" -#include "return_function.h" +#include "aware_function.h" namespace rtl::cache { @@ -27,15 +27,15 @@ namespace rtl::cache return instance_; } - const dispatch::lambda_function& push(const dispatch::functor& fptr) const + const dispatch::lambda_function& push(const dispatch::functor& p_functor) const { - m_erasure_cache.push_back(erase::return_function()); - erase::function* erasure = &m_erasure_cache.back(); + m_erasure_cache.push_back(erase::aware_function()); + erase::erased_function* erasure = &m_erasure_cache.back(); - m_cache.push_back(dispatch::lambda_function(fptr, erasure)); - fptr.m_lambda = &m_cache.back(); + m_cache.push_back(dispatch::lambda_function(p_functor, erasure)); + p_functor.m_lambda = &m_cache.back(); - (m_cache.back()).template init_erasure(); + (m_erasure_cache.back()).m_function = m_cache.back().template get_hopper(); return m_cache.back(); } @@ -48,7 +48,7 @@ namespace rtl::cache // No reallocation occurs; original objects stay intact mutable std::list> m_cache; - mutable std::list> m_erasure_cache; + mutable std::list> m_erasure_cache; lambda_function() = default; }; diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h index 28a6c235..50e00856 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h @@ -13,9 +13,9 @@ #include +#include "aware_method.h" #include "lambda_method.h" -#include "return_method.h" -#include "return_const_method.h" +#include "aware_method_const.h" namespace rtl::cache { @@ -28,15 +28,15 @@ namespace rtl::cache return instance_; } - const dispatch::lambda_method& push(const dispatch::functor& fptr) const + const dispatch::lambda_method& push(const dispatch::functor& p_functor) const { - m_erasure_cache.push_back(erase::return_method()); - erase::method* erasure = &m_erasure_cache.back(); + m_erasure_cache.push_back(erase::aware_method()); + erase::erased_method* erasure = &m_erasure_cache.back(); - m_cache.push_back(dispatch::lambda_method(fptr, erasure)); - fptr.m_lambda = &m_cache.back(); + m_cache.push_back(dispatch::lambda_method(p_functor, erasure)); + p_functor.m_lambda = &m_cache.back(); - (m_cache.back()).template init_erasure(); + (m_erasure_cache.back()).m_method = m_cache.back().template get_hopper(); return m_cache.back(); } @@ -50,7 +50,7 @@ namespace rtl::cache // No reallocation occurs; original objects stay intact mutable std::list> m_cache; - mutable std::list> m_erasure_cache; + mutable std::list> m_erasure_cache; lambda_method() = default; }; diff --git a/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h index 59ce1144..bfe749f7 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_method_ptr.h @@ -13,7 +13,7 @@ #include -#include "method_ptr.h" +#include "functor_method.h" namespace rtl::cache { diff --git a/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h b/ReflectionTemplateLib/rtl/cache/cache_method_ptr_const.h similarity index 98% rename from ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h rename to ReflectionTemplateLib/rtl/cache/cache_method_ptr_const.h index 3cc9783d..3a548048 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_const_method_ptr.h +++ b/ReflectionTemplateLib/rtl/cache/cache_method_ptr_const.h @@ -13,7 +13,7 @@ #include -#include "const_method_ptr.h" +#include "functor_method_const.h" namespace rtl::cache { diff --git a/ReflectionTemplateLib/rtl/detail/inc/CallReflector.h b/ReflectionTemplateLib/rtl/detail/inc/CallReflector.h index 775b6786..98f77596 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/CallReflector.h +++ b/ReflectionTemplateLib/rtl/detail/inc/CallReflector.h @@ -31,7 +31,7 @@ namespace rtl::detail { * gets the lambda vector from '_derivedType' and calls the lambda at given index with '_args'. * this 'forwardCall' is for calling lambda containing non-member-function and static-member-function functors. */ template - FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, _params&&..._args) + ForceInline static Return forwardCall(const detail::FunctorId& pFunctorId, _params&&..._args) { //'getOverloads()' must be implemented by _derivedType (FunctorContainer). return _derivedType::getOverloads()[pFunctorId.m_lambdaIndex](pFunctorId, std::forward<_params>(_args)...); @@ -43,7 +43,7 @@ namespace rtl::detail { * gets the lambda vector from '_derivedType' and calls the lambda at given index with '_args'. * this 'forwardCall' is for calling lambda containing constructors. */ template - FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, rtl::alloc pAllocType, const detail::FunctorId& pClonerId, _params&&..._args) + ForceInline static Return forwardCall(const detail::FunctorId& pFunctorId, rtl::alloc pAllocType, const detail::FunctorId& pClonerId, _params&&..._args) { //'getOverloads()' must be implemented by _derivedType (FunctorContainer). return _derivedType::getOverloads()[pFunctorId.m_lambdaIndex](pFunctorId, pAllocType, pClonerId, std::forward<_params>(_args)...); @@ -51,7 +51,7 @@ namespace rtl::detail { template - FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, const RObject& pSrcObj, rtl::alloc pAllocType) + ForceInline static Return forwardCall(const detail::FunctorId& pFunctorId, const RObject& pSrcObj, rtl::alloc pAllocType) { //'getOverloads()' must be implemented by _derivedType (FunctorContainer). return _derivedType::getOverloads()[pFunctorId.m_lambdaIndex](pFunctorId, pSrcObj, pAllocType); @@ -63,7 +63,7 @@ namespace rtl::detail { * gets the lambda vector from '_derivedType' and calls the lambda at given index with '_args'. * this 'forwardCall' is for calling lambda containing member-function functors. */ template - FORCE_INLINE static Return forwardCall(const detail::FunctorId& pFunctorId, const rtl::RObject& pTarget, _params&&..._args) + ForceInline static Return forwardCall(const detail::FunctorId& pFunctorId, const rtl::RObject& pTarget, _params&&..._args) { //'getMethodFunctors()' is implemented by _derivedType (MethodContainer) return _derivedType::getMethodFunctors()[pFunctorId.m_lambdaIndex](pFunctorId, pTarget, std::forward<_params>(_args)...); diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index 491a9c89..b322b959 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -16,13 +16,13 @@ #include "FunctionCaller.h" #include "FunctorContainer.h" -#include "erase_function.h" +#include "erased_function.h" namespace rtl::detail { template template - FORCE_INLINE Return FunctionCaller<_signature...>::call(_args&&...params) const noexcept + ForceInline Return FunctionCaller<_signature...>::call(_args&&...params) const noexcept { using Container = std::conditional_t...>, @@ -50,7 +50,7 @@ namespace rtl::detail { auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { - functorId->template get_lambda_function<_args...>()->m_erasure->hop_v(std::forward<_args>(params)...); + functorId->template get_lambda_function<_args...>()->m_erasure->void_hop(std::forward<_args>(params)...); } return error::None; } @@ -58,11 +58,11 @@ namespace rtl::detail template template - FORCE_INLINE std::any FunctionCaller<_signature...>::call_r(_args&& ...params) const noexcept + ForceInline std::any FunctionCaller<_signature...>::call_r(_args&& ...params) const noexcept { auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { - return functorId->template get_lambda_function<_args...>()->m_erasure->hop_r(std::forward<_args>(params)...); + return functorId->template get_lambda_function<_args...>()->m_erasure->return_hop(std::forward<_args>(params)...); } return std::any(); } diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h index 02cc947b..2e7f529e 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h @@ -11,7 +11,7 @@ #pragma once -#include "erase_method.h" +#include "erased_method.h" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index c8e6d4ee..4c1dbb13 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -24,7 +24,7 @@ namespace rtl::detail * invokes non-static-member-function functor associated with 'm_method' on object 'm_target'. */ template template - FORCE_INLINE Return DefaultInvoker<_signature...>::call(_args&& ...params) const noexcept + ForceInline Return DefaultInvoker<_signature...>::call(_args&& ...params) const noexcept { //Only static-member-functions have Qualifier- 'methodQ::None' if (m_method->getQualifier() == methodQ::None) [[unlikely]] { @@ -55,7 +55,7 @@ namespace rtl::detail template template template - FORCE_INLINE Return + ForceInline Return DefaultInvoker<_signature...>::Invoker<_invokSignature...>::invoke(const Method& pMethod, const RObject& pTarget, _args&&... params) @@ -93,7 +93,7 @@ namespace rtl::detail * invokes non-static-member-function functor associated with 'm_method' on object 'm_target'. */ template template - FORCE_INLINE Return NonConstInvoker<_signature...>::call(_args&& ...params) const noexcept + ForceInline Return NonConstInvoker<_signature...>::call(_args&& ...params) const noexcept { if (m_method->getQualifier() == methodQ::None) [[unlikely]] { return static_cast(*m_method).bind().call(std::forward<_args>(params)...); @@ -122,7 +122,7 @@ namespace rtl::detail template template template - FORCE_INLINE Return + ForceInline Return NonConstInvoker<_signature...>::Invoker<_invokSignature...>::invoke(const Method& pMethod, const RObject& pTarget, _args&&... params) @@ -191,18 +191,18 @@ namespace rtl::detail { auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { - functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->hop_v(m_target, std::forward<_args>(params)...); + functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->void_hop(m_target, std::forward<_args>(params)...); } return error::None; } template template - FORCE_INLINE std::any ErasedInvoker<_recordType>::call_r(_args&&...params) const noexcept + ForceInline std::any ErasedInvoker<_recordType>::call_r(_args&&...params) const noexcept { auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { - return functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->hop_r(m_target, std::forward<_args>(params)...); + return functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->return_hop(m_target, std::forward<_args>(params)...); } return std::any(); } diff --git a/ReflectionTemplateLib/rtl/detail/inc/RObjExtracter.h b/ReflectionTemplateLib/rtl/detail/inc/RObjExtracter.h index 8f1c11ef..14ab3623 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/RObjExtracter.h +++ b/ReflectionTemplateLib/rtl/detail/inc/RObjExtracter.h @@ -22,7 +22,7 @@ namespace rtl::detail const RObject* m_rObj; template - FORCE_INLINE static const T* getPointer(const std::any& pObject, const EntityKind pEntityKind) noexcept + ForceInline static const T* getPointer(const std::any& pObject, const EntityKind pEntityKind) noexcept { switch (pEntityKind) { @@ -39,7 +39,7 @@ namespace rtl::detail template - FORCE_INLINE const T* getPointer() const noexcept + ForceInline const T* getPointer() const noexcept { switch (m_rObj->m_objectId.m_containsAs) { @@ -59,7 +59,7 @@ namespace rtl::detail template = 0> - FORCE_INLINE auto getWrapper() const noexcept -> const RObjectUPtr::value_type>* + ForceInline auto getWrapper() const noexcept -> const RObjectUPtr::value_type>* { if (m_rObj->m_objectId.m_wrapperType == detail::Wrapper::Unique) { @@ -83,7 +83,7 @@ namespace rtl::detail template = 0> - FORCE_INLINE const T* getWrapper() const noexcept + ForceInline const T* getWrapper() const noexcept { if (m_rObj->m_objectId.m_wrapperType == detail::Wrapper::Shared) { @@ -106,7 +106,7 @@ namespace rtl::detail template - FORCE_INLINE const T* getFromWrapper() const noexcept + ForceInline const T* getFromWrapper() const noexcept { if constexpr (std::is_destructible_v) { diff --git a/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h b/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h index cab52049..bb43306b 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h @@ -39,7 +39,7 @@ namespace rtl::detail GETTER(EntityKind, ContainedAs, m_containsAs) template - FORCE_INLINE static constexpr EntityKind getEntityKind() noexcept + ForceInline static constexpr EntityKind getEntityKind() noexcept { using W = traits::std_wrapper>; using _T = traits::raw_t>; @@ -59,7 +59,7 @@ namespace rtl::detail template - FORCE_INLINE static RObjectId create(std::optional pClonerId, bool pIsConstCastSafe) noexcept + ForceInline static RObjectId create(std::optional pClonerId, bool pIsConstCastSafe) noexcept { // extract wrapper info. using _W = traits::std_wrapper>; diff --git a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt index cf3b911f..efec0dc1 100644 --- a/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/dispatch/CMakeLists.txt @@ -4,17 +4,18 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/functor.h" - "${CMAKE_CURRENT_SOURCE_DIR}/function_ptr.h" - "${CMAKE_CURRENT_SOURCE_DIR}/method_ptr.h" - "${CMAKE_CURRENT_SOURCE_DIR}/const_method_ptr.h" + + "${CMAKE_CURRENT_SOURCE_DIR}/functor_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/functor_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/functor_method_const.h" "${CMAKE_CURRENT_SOURCE_DIR}/lambda.h" "${CMAKE_CURRENT_SOURCE_DIR}/lambda_method.h" "${CMAKE_CURRENT_SOURCE_DIR}/lambda_function.h" - "${CMAKE_CURRENT_SOURCE_DIR}/rtl_function.h" "${CMAKE_CURRENT_SOURCE_DIR}/rtl_method.h" - "${CMAKE_CURRENT_SOURCE_DIR}/rtl_const_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/rtl_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/rtl_method_const.h" ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/dispatch/function_ptr.h b/ReflectionTemplateLib/rtl/dispatch/functor_function.h similarity index 100% rename from ReflectionTemplateLib/rtl/dispatch/function_ptr.h rename to ReflectionTemplateLib/rtl/dispatch/functor_function.h diff --git a/ReflectionTemplateLib/rtl/dispatch/method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/functor_method.h similarity index 100% rename from ReflectionTemplateLib/rtl/dispatch/method_ptr.h rename to ReflectionTemplateLib/rtl/dispatch/functor_method.h diff --git a/ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h b/ReflectionTemplateLib/rtl/dispatch/functor_method_const.h similarity index 100% rename from ReflectionTemplateLib/rtl/dispatch/const_method_ptr.h rename to ReflectionTemplateLib/rtl/dispatch/functor_method_const.h diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index efd7d7df..2e62c42d 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -12,9 +12,9 @@ #pragma once #include "lambda.h" -#include "function_ptr.h" #include "rtl_function.h" -#include "return_function.h" +#include "functor_function.h" +#include "erased_function.h" namespace rtl::dispatch { @@ -24,20 +24,13 @@ namespace rtl::dispatch template using hopper_t = rtl::function; - erase::function* m_erasure; + erase::erased_function* m_erasure; - lambda_function(const functor& p_functor, erase::function* p_erasure) noexcept + lambda_function(const functor& p_functor, erase::erased_function* p_erasure) noexcept : lambda_base(p_functor) , m_erasure(p_erasure) { } - template - constexpr void init_erasure() const - { - auto erasure = static_cast*>(m_erasure); - erasure->m_function = get_hopper(); - } - template constexpr const hopper_t get_hopper(const std::size_t p_returnId = 0) const { diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index cfc3d954..6e5c1cc6 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -12,11 +12,10 @@ #pragma once #include "lambda.h" -#include "method_ptr.h" #include "rtl_method.h" -#include "rtl_const_method.h" -#include "return_method.h" -#include "return_const_method.h" +#include "erased_method.h" +#include "functor_method.h" +#include "rtl_method_const.h" namespace rtl::dispatch @@ -30,20 +29,13 @@ namespace rtl::dispatch template using hopper_ct = rtl::method; - erase::method* m_erasure; + erase::erased_method* m_erasure; - lambda_method(const functor& p_functor, erase::method* p_erasure) noexcept + lambda_method(const functor& p_functor, erase::erased_method* p_erasure) noexcept : lambda_base(p_functor) , m_erasure(p_erasure) { } - template - constexpr void init_erasure() const - { - auto erasure = static_cast*>(m_erasure); - erasure->m_method = get_hopper(); - } - template requires (std::is_const_v == false) constexpr const hopper_t get_hopper(std::size_t p_returnId = 0) const { diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_const_method.h b/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h similarity index 100% rename from ReflectionTemplateLib/rtl/dispatch/rtl_const_method.h rename to ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h diff --git a/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt b/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt index da69ba9b..b2f4a6d3 100644 --- a/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt @@ -2,11 +2,13 @@ # Collect headers in this folder (absolute paths) set(LOCAL_HEADERS - "${CMAKE_CURRENT_SOURCE_DIR}/erase_function.h" - "${CMAKE_CURRENT_SOURCE_DIR}/erase_method.h" - "${CMAKE_CURRENT_SOURCE_DIR}/return_function.h" - "${CMAKE_CURRENT_SOURCE_DIR}/return_method.h" - "${CMAKE_CURRENT_SOURCE_DIR}/return_const_method.h" + + "${CMAKE_CURRENT_SOURCE_DIR}/erased_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/erased_function.h" + + "${CMAKE_CURRENT_SOURCE_DIR}/aware_method.h" + "${CMAKE_CURRENT_SOURCE_DIR}/aware_function.h" + "${CMAKE_CURRENT_SOURCE_DIR}/aware_method_const.h" ) target_sources(ReflectionTemplateLib PRIVATE ${LOCAL_HEADERS}) diff --git a/ReflectionTemplateLib/rtl/erasure/return_function.h b/ReflectionTemplateLib/rtl/erasure/aware_function.h similarity index 66% rename from ReflectionTemplateLib/rtl/erasure/return_function.h rename to ReflectionTemplateLib/rtl/erasure/aware_function.h index 54b2d1e0..b139055d 100644 --- a/ReflectionTemplateLib/rtl/erasure/return_function.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_function.h @@ -11,48 +11,46 @@ #pragma once -#include "erase_function.h" +#include "erased_function.h" #include "rtl_function.h" namespace rtl::erase { template - struct return_function : public function + struct aware_function : public erased_function { - using base_t = function; + rtl::function m_function; - using this_t = return_function; + using base_t = erased_function; - rtl::function m_function; + using this_t = aware_function; - return_function() + aware_function() { - base_t::v_hop = hop_v; - base_t::r_hop = hop_r; + base_t::hop_void = void_hop; + base_t::hop_return = return_hop; } - FORCE_INLINE static void hop_v(base_t* p_this, signature_ts&&...params) + constexpr static void void_hop(const base_t* p_this, signature_ts&&...params) noexcept { if constexpr (std::is_void_v) { - auto this_p = static_cast(p_this); + auto this_p = static_cast(p_this); this_p->m_function(std::forward(params)...); } } - FORCE_INLINE static std::any hop_r(base_t* p_this, signature_ts&&...params) + ForceInline static std::any return_hop(const base_t* p_this, signature_ts&&...params) noexcept { if constexpr (!std::is_void_v) { - auto this_p = static_cast(p_this); + auto this_p = static_cast(p_this); auto&& ret_v = this_p->m_function(std::forward(params)...); - if constexpr (std::is_reference_v) - { + if constexpr (std::is_reference_v) { return std::any(&ret_v); } - else - { + else { return std::any(std::forward(ret_v)); } } diff --git a/ReflectionTemplateLib/rtl/erasure/return_method.h b/ReflectionTemplateLib/rtl/erasure/aware_method.h similarity index 65% rename from ReflectionTemplateLib/rtl/erasure/return_method.h rename to ReflectionTemplateLib/rtl/erasure/aware_method.h index 3129c06f..784cfb65 100644 --- a/ReflectionTemplateLib/rtl/erasure/return_method.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_method.h @@ -11,47 +11,45 @@ #pragma once -#include "erase_method.h" +#include "erased_method.h" namespace rtl::erase { template - struct return_method : public method + struct aware_method : public erased_method { - using base_t = method; + using base_t = erased_method; - using this_t = return_method; + using this_t = aware_method; rtl::method m_method; - return_method() + aware_method() { - base_t::v_hop = hop_v; - base_t::r_hop = hop_r; + base_t::hop_void = void_hop; + base_t::hop_return = return_hop; } - FORCE_INLINE static void hop_v(base_t* p_this, const record_t& p_target, signature_ts&&...params) + constexpr static void void_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept { if constexpr (std::is_void_v) { - auto this_p = static_cast(p_this); + auto this_p = static_cast(p_this); this_p->m_method(const_cast(p_target), std::forward(params)...); } } - FORCE_INLINE static std::any hop_r(base_t* p_this, const record_t& p_target, signature_ts&&...params) + ForceInline static std::any return_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept { if constexpr (!std::is_void_v) { - auto this_p = static_cast(p_this); + auto this_p = static_cast(p_this); auto&& ret_v = this_p->m_method(const_cast(p_target), std::forward(params)...); - if constexpr (std::is_reference_v) - { + if constexpr (std::is_reference_v) { return std::any(&ret_v); } - else - { + else { return std::any(std::forward(ret_v)); } } diff --git a/ReflectionTemplateLib/rtl/erasure/return_const_method.h b/ReflectionTemplateLib/rtl/erasure/aware_method_const.h similarity index 63% rename from ReflectionTemplateLib/rtl/erasure/return_const_method.h rename to ReflectionTemplateLib/rtl/erasure/aware_method_const.h index a47f8521..5caedf3a 100644 --- a/ReflectionTemplateLib/rtl/erasure/return_const_method.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_method_const.h @@ -11,47 +11,45 @@ #pragma once -#include "erase_method.h" +#include "erased_method.h" namespace rtl::erase { template - struct return_method : public method + struct aware_method : public erased_method { - using base_t = method; + using base_t = erased_method; - using this_t = return_method; + using this_t = aware_method; rtl::method m_method; - return_method() + aware_method() { - base_t::v_hop = hop_v; - base_t::r_hop = hop_r; + base_t::v_hop = void_hop; + base_t::r_hop = return_hop; } - FORCE_INLINE static void hop_v(base_t* p_this, const record_t& p_target, signature_ts&&...params) + constexpr static void void_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept { if constexpr (std::is_void_v) { - auto this_p = static_cast(p_this); + auto this_p = static_cast(p_this); this_p->m_method(p_target, std::forward(params)...); } } - FORCE_INLINE static std::any hop_r(base_t* p_this, const record_t& p_target, signature_ts&&...params) + ForceInline static std::any return_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept { if constexpr (!std::is_void_v) { - auto this_p = static_cast(p_this); + auto this_p = static_cast(p_this); auto&& ret_v = this_p->m_method(p_target, std::forward(params)...); - if constexpr (std::is_reference_v) - { + if constexpr (std::is_reference_v) { return std::any(&ret_v); } - else - { + else { return std::any(std::forward(ret_v)); } } diff --git a/ReflectionTemplateLib/rtl/erasure/erase_function.h b/ReflectionTemplateLib/rtl/erasure/erased_function.h similarity index 57% rename from ReflectionTemplateLib/rtl/erasure/erase_function.h rename to ReflectionTemplateLib/rtl/erasure/erased_function.h index dd6012be..30050564 100644 --- a/ReflectionTemplateLib/rtl/erasure/erase_function.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_function.h @@ -17,26 +17,28 @@ namespace rtl::erase { template - struct function + struct erased_function { - using this_t = function; + constexpr void void_hop(signature_ts&&...params) const noexcept + { + (*hop_void)(this, std::forward(params)...); + } - using functor_vt = void(*)(this_t*, signature_ts&&...); + ForceInline std::any return_hop(signature_ts&&...params) const noexcept + { + return (*hop_return)(this, std::forward(params)...); + } - using functor_rt = std::any(*)(this_t*, signature_ts&&...); + protected: - functor_vt v_hop = nullptr; + using this_t = erased_function; - functor_rt r_hop = nullptr; + using functor_vt = void(*)(const this_t*, signature_ts&&...); - FORCE_INLINE void hop_v(signature_ts&&...params) - { - v_hop(this, std::forward(params)...); - } + using functor_rt = std::any(*)(const this_t*, signature_ts&&...); - FORCE_INLINE std::any hop_r(signature_ts&&...params) - { - return r_hop(this, std::forward(params)...); - } + functor_vt hop_void = nullptr; + + functor_rt hop_return = nullptr; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erase_method.h b/ReflectionTemplateLib/rtl/erasure/erased_method.h similarity index 54% rename from ReflectionTemplateLib/rtl/erasure/erase_method.h rename to ReflectionTemplateLib/rtl/erasure/erased_method.h index a90ffbf7..56050586 100644 --- a/ReflectionTemplateLib/rtl/erasure/erase_method.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_method.h @@ -17,26 +17,28 @@ namespace rtl::erase { template - struct method + struct erased_method { - using this_t = method; + constexpr void void_hop(const record_t& p_target, signature_ts&&...params) const noexcept + { + (*hop_void)(this, p_target, std::forward(params)...); + } - using functor_vt = void(*)(this_t*, const record_t&, signature_ts&&...); + ForceInline std::any return_hop(const record_t& p_target, signature_ts&&...params) const noexcept + { + return (*hop_return)(this, p_target, std::forward(params)...); + } - using functor_rt = std::any(*)(this_t*, const record_t&, signature_ts&&...); + protected: - functor_vt v_hop = nullptr; + using this_t = erased_method; - functor_rt r_hop = nullptr; + using functor_vt = void(*)(const this_t*, const record_t&, signature_ts&&...); - FORCE_INLINE void hop_v(const record_t& p_target, signature_ts&&...params) - { - v_hop(this, p_target, std::forward(params)...); - } + using functor_rt = std::any(*)(const this_t*, const record_t&, signature_ts&&...); - FORCE_INLINE std::any hop_r(const record_t& p_target, signature_ts&&...params) - { - return r_hop(this, p_target, std::forward(params)...); - } + functor_vt hop_void = nullptr; + + functor_rt hop_return = nullptr; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index ebc2d6f8..e728d6c4 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -63,7 +63,7 @@ namespace rtl * a 'Function' object may be associated with multiple functors in case of overloads. * every overload will have unique 'FunctorId', contained by one 'Function' object. * given signatureId is compared against the signatureId of all overloads registered. -*/ FORCE_INLINE const std::size_t Function::hasSignatureId(const std::size_t pSignatureId) const +*/ ForceInline const std::size_t Function::hasSignatureId(const std::size_t pSignatureId) const { //simple linear-search, efficient for small set of elements. for (const auto& functorId : m_functorIds) { @@ -75,7 +75,7 @@ namespace rtl } - FORCE_INLINE const detail::FunctorId* Function::hasFunctorId(const std::size_t pSignatureId) const + ForceInline const detail::FunctorId* Function::hasFunctorId(const std::size_t pSignatureId) const { //simple linear-search, efficient for small set of elements. for (const auto& functorId : m_functorIds) { @@ -87,7 +87,7 @@ namespace rtl } - FORCE_INLINE const detail::FunctorId* Function::getLambdaById(const std::size_t pSignatureId) const + ForceInline const detail::FunctorId* Function::getLambdaById(const std::size_t pSignatureId) const { //simple linear-search, efficient for small set of elements. for (const auto& functorId : m_functorIds) { diff --git a/ReflectionTemplateLib/rtl/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp index 91f7c56f..9e63f222 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.hpp +++ b/ReflectionTemplateLib/rtl/inc/Method.hpp @@ -16,14 +16,14 @@ namespace rtl { template - FORCE_INLINE const detail::DefaultInvoker<_signature...> Method::bind(const RObject& pTarget) const + ForceInline const detail::DefaultInvoker<_signature...> Method::bind(const RObject& pTarget) const { return detail::DefaultInvoker<_signature...>{ this, &pTarget }; } template - FORCE_INLINE const detail::NonConstInvoker<_signature...> Method::bind(constCast&& pTarget) const + ForceInline const detail::NonConstInvoker<_signature...> Method::bind(constCast&& pTarget) const { return detail::NonConstInvoker<_signature...>{ this, &pTarget.m_target }; } diff --git a/ReflectionTemplateLib/rtl/inc/RObject.hpp b/ReflectionTemplateLib/rtl/inc/RObject.hpp index 51091c24..35802478 100644 --- a/ReflectionTemplateLib/rtl/inc/RObject.hpp +++ b/ReflectionTemplateLib/rtl/inc/RObject.hpp @@ -25,7 +25,7 @@ namespace rtl { - FORCE_INLINE RObject::RObject(std::any&& pObject, detail::RObjectId&& pRObjId, + ForceInline RObject::RObject(std::any&& pObject, detail::RObjectId&& pRObjId, const std::vector* pConverters) noexcept : m_object(std::in_place, std::move(pObject)) , m_objectId(pRObjId) @@ -120,7 +120,7 @@ namespace rtl template , int>> - FORCE_INLINE std::optional> RObject::view() const noexcept + ForceInline std::optional> RObject::view() const noexcept { if (isEmpty()) { return std::nullopt; @@ -140,7 +140,7 @@ namespace rtl template , int>> - FORCE_INLINE std::optional> RObject::view() const noexcept + ForceInline std::optional> RObject::view() const noexcept { if (isEmpty()) { return std::nullopt; @@ -161,7 +161,7 @@ namespace rtl template , int>> - FORCE_INLINE std::optional> RObject::view() const noexcept + ForceInline std::optional> RObject::view() const noexcept { if (isEmpty()) { return std::nullopt; diff --git a/ReflectionTemplateLib/rtl/rtl_constants.h b/ReflectionTemplateLib/rtl/rtl_constants.h index aeb28150..9ee16c65 100644 --- a/ReflectionTemplateLib/rtl/rtl_constants.h +++ b/ReflectionTemplateLib/rtl/rtl_constants.h @@ -169,10 +169,10 @@ namespace rtl::detail } #if defined(_MSC_VER) -#define FORCE_INLINE __forceinline +#define ForceInline __forceinline #elif defined(__GNUC__) || defined(__clang__) -#define FORCE_INLINE inline __attribute__((always_inline)) +#define ForceInline inline __attribute__((always_inline)) #else -#define FORCE_INLINE inline +#define ForceInline inline #endif } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/rtl_errors.h b/ReflectionTemplateLib/rtl/rtl_errors.h index 4dc5e28c..153008c3 100644 --- a/ReflectionTemplateLib/rtl/rtl_errors.h +++ b/ReflectionTemplateLib/rtl/rtl_errors.h @@ -49,7 +49,7 @@ namespace rtl case error::CloningDisabled: return "Type not registered: The requested type is not explicitly registered in the Reflection system"; case error::FunctionNotRegistered: - return "Function not registered: The requested function/method is not registered in the Reflection system"; + return "Function not registered: The requested erase_function/method is not registered in the Reflection system"; case error::TargetMismatch: return "The object you're trying to bind doesn't match the expected type of the method."; case error::NonConstOverloadMissing: diff --git a/ReflectionTemplateLib/rtl/rtl_forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h index 5d5c391e..228a29dd 100644 --- a/ReflectionTemplateLib/rtl/rtl_forward_decls.h +++ b/ReflectionTemplateLib/rtl/rtl_forward_decls.h @@ -34,16 +34,16 @@ namespace rtl namespace erase { template - struct function; + struct erased_function; template - struct method; + struct erased_method; template - struct return_function; + struct aware_function; template - struct return_method; + struct aware_method; } namespace detail diff --git a/ReflectionTemplateLib/rtl/rtl_typeid.h b/ReflectionTemplateLib/rtl/rtl_typeid.h index 8fe1d88e..fa5158f4 100644 --- a/ReflectionTemplateLib/rtl/rtl_typeid.h +++ b/ReflectionTemplateLib/rtl/rtl_typeid.h @@ -16,11 +16,11 @@ #include #if defined(_MSC_VER) -#define FORCE_INLINE __forceinline +#define ForceInline __forceinline #elif defined(__GNUC__) || defined(__clang__) -#define FORCE_INLINE inline __attribute__((always_inline)) +#define ForceInline inline __attribute__((always_inline)) #else -#define FORCE_INLINE inline +#define ForceInline inline #endif namespace rtl { @@ -46,7 +46,7 @@ namespace rtl { //'0' represents no type. [Never change, critical.] static constexpr const std::size_t None = 0; - FORCE_INLINE static std::size_t get() + ForceInline static std::size_t get() { if constexpr (!std::is_same_v<_type, std::nullptr_t>) { From ef1be6ccb48f04f4c368e296a0de087e005dd6f2 Mon Sep 17 00:00:00 2001 From: neeraj Date: Tue, 30 Sep 2025 14:10:47 +0530 Subject: [PATCH 50/58] return erased-type boxed in RObject, integrated. --- .../src/ReflectedCallUnknownReturn.cpp | 50 +++++++++---------- .../NameSpaceGlobalsTests.cpp | 12 ++--- .../rtl/builder/SetupFunction.hpp | 4 +- .../rtl/builder/SetupMethod.hpp | 5 +- .../rtl/cache/cache_lambda_function.h | 3 +- .../rtl/cache/cache_lambda_method.h | 2 +- .../rtl/detail/inc/CMakeLists.txt | 1 + .../rtl/detail/inc/FunctionCaller.h | 8 --- .../rtl/detail/inc/FunctionCaller.hpp | 38 +++++--------- .../rtl/detail/inc/FunctorId.h | 23 ++++----- .../rtl/detail/inc/FunctorId.hpp | 32 ++++++++++++ .../rtl/detail/inc/MethodInvoker.h | 8 ++- .../rtl/detail/inc/MethodInvoker.hpp | 32 ++++++------ .../rtl/detail/inc/RObjectId.h | 2 - .../rtl/detail/inc/RObjectUPtr.h | 9 ++-- .../rtl/detail/inc/ReflectCast.h | 4 +- ReflectionTemplateLib/rtl/dispatch/lambda.h | 9 +++- .../rtl/erasure/aware_function.h | 30 ++++++++--- .../rtl/erasure/aware_method.h | 26 +++++++--- .../rtl/erasure/aware_method_const.h | 27 +++++++--- .../rtl/erasure/erased_function.h | 5 +- .../rtl/erasure/erased_method.h | 5 +- ReflectionTemplateLib/rtl/inc/Function.h | 8 +-- ReflectionTemplateLib/rtl/inc/Function.hpp | 4 +- ReflectionTemplateLib/rtl/inc/Method.h | 3 +- ReflectionTemplateLib/rtl/inc/RObject.h | 9 +++- ReflectionTemplateLib/rtl/inc/RObject.hpp | 8 +-- ReflectionTemplateLib/rtl/rtl_forward_decls.h | 2 +- ReflectionTemplateLib/rtl/src/CxxMirror.cpp | 2 +- ReflectionTemplateLib/rtl/src/Function.cpp | 1 + 30 files changed, 209 insertions(+), 163 deletions(-) create mode 100644 ReflectionTemplateLib/rtl/detail/inc/FunctorId.hpp diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index 81e287b1..294f8f60 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -69,20 +69,20 @@ namespace return *method; }(); - static const rtl::RObject nodeObj = []() - { - std::optional Node = cxx::mirror().getRecord("Node"); - if (!Node) { - std::cerr << "[x] error: record 'Node' not found.\n"; - std::abort(); - } - - auto [err, robj] = Node->create(); - if (robj.isEmpty()) { - std::cout << "[x] error: " << rtl::to_string(err) << "\n"; - } - return std::move(robj); - }(); + // static const rtl::RObject nodeObj = []() + // { + // std::optional Node = cxx::mirror().getRecord("Node"); + // if (!Node) { + // std::cerr << "[x] error: record 'Node' not found.\n"; + // std::abort(); + // } + + // auto [err, robj] = Node->create(); + // if (robj.isEmpty()) { + // std::cout << "[x] error: " << rtl::to_string(err) << "\n"; + // } + // return std::move(robj); + // }(); } @@ -90,7 +90,7 @@ namespace { static auto _test0 = []() { - auto err = SendMessage(bm::g_longStr).err; + auto err = SendMessage()(bm::g_longStr).err; if (err != rtl::error::None) { std::cout << "[00] error: " << rtl::to_string(err) << "\n"; } @@ -99,7 +99,7 @@ namespace static auto _test1 = []() { - auto err = NodeSendMessage(nodeObj)(bm::g_longStr).err; + auto err = NodeSendMessage(bm::Node())(bm::g_longStr).err; if (err != rtl::error::None) { std::cout << "[01] error: " << rtl::to_string(err) << "\n"; } @@ -108,7 +108,7 @@ namespace static auto _test2 = []() { - auto err = GetMessage(bm::g_longStr).err; + auto err = GetMessage()(bm::g_longStr).err; if (err != rtl::error::None) { std::cout << "[02] error: " << rtl::to_string(err) << "\n"; } @@ -117,7 +117,7 @@ namespace static auto _test3 = []() { - auto err = NodeGetMessage(nodeObj)(bm::g_longStr).err; + auto err = NodeGetMessage(bm::Node())(bm::g_longStr).err; if (err != rtl::error::None) { std::cout << "[03] error: " << rtl::to_string(err) << "\n"; } @@ -134,23 +134,22 @@ namespace void RtlFunction_call_ReturnUnknown::typeVoid(benchmark::State& state) { - static auto __=_new_line(); + static auto __= _new_line(); static auto _ = _test0(); for (auto _ : state) { - SendMessage.bind().call_v(bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done); + benchmark::DoNotOptimize(SendMessage()(bm::g_longStr)); } } void RtlFunction_call_ReturnUnknown::typeNonVoid(benchmark::State& state) { - static auto __=_new_line(); + static auto __= _new_line(); static auto _ = _test2(); for (auto _ : state) { - benchmark::DoNotOptimize(GetMessage.bind().call_r(bm::g_longStr)); + benchmark::DoNotOptimize(GetMessage()(bm::g_longStr)); } } @@ -161,8 +160,7 @@ void RtlFunction_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) static bm::Node node; for (auto _ : state) { - NodeSendMessage(node).call_v(bm::g_longStr); - benchmark::DoNotOptimize(bm::g_work_done->c_str()); + benchmark::DoNotOptimize(NodeSendMessage(node)(bm::g_longStr)); } } @@ -173,6 +171,6 @@ void RtlFunction_callMethod_ReturnUnknown::typeNonVoid(benchmark::State& state) static bm::Node node; for (auto _ : state) { - benchmark::DoNotOptimize(NodeGetMessage(node).call_r(bm::g_longStr)); + benchmark::DoNotOptimize(NodeGetMessage(node)(bm::g_longStr)); } } \ No newline at end of file diff --git a/RTLTestRunApp/src/FunctionalityTests/NameSpaceGlobalsTests.cpp b/RTLTestRunApp/src/FunctionalityTests/NameSpaceGlobalsTests.cpp index 705e5beb..b236aa79 100644 --- a/RTLTestRunApp/src/FunctionalityTests/NameSpaceGlobalsTests.cpp +++ b/RTLTestRunApp/src/FunctionalityTests/NameSpaceGlobalsTests.cpp @@ -144,7 +144,7 @@ namespace rtl_tests double real = g_real; //g_real's type is "const double", so can't be passed directly to setReal else, //its type will be inferred 'const double' instead of 'double'. - auto [err0, ret0] = (*setReal)(real); + auto [err0, ret0] = setReal->bind().call(real); EXPECT_TRUE(err0 == rtl::error::None); ASSERT_TRUE(ret0.isEmpty()); @@ -152,13 +152,13 @@ namespace rtl_tests double imaginary = g_imaginary; //g_imaginary's type is "const double", so can't be passed directly to setImaginary else, //its type will be inferred 'const double' instead of 'double'. - auto [err1, ret1] = (*setImaginary)(imaginary); + auto [err1, ret1] = setImaginary->bind().call(imaginary); EXPECT_TRUE(err1 == rtl::error::None); ASSERT_TRUE(ret1.isEmpty()); EXPECT_TRUE(getMagnitude->hasSignature<>()); //empty template params checks for zero arguments. - auto [err2, ret2] = (*getMagnitude)(); + auto [err2, ret2] = getMagnitude->bind().call(); EXPECT_TRUE(err2 == rtl::error::None); ASSERT_FALSE(ret2.isEmpty()); @@ -194,7 +194,7 @@ namespace rtl_tests optional getComplexNumAsString = cxx::mirror().getFunction(str_getComplexNumAsString); ASSERT_TRUE(getComplexNumAsString); - auto [err, ret] = (*getComplexNumAsString)(); + auto [err, ret] = getComplexNumAsString->bind().call(); EXPECT_TRUE(err == rtl::error::None); ASSERT_FALSE(ret.isEmpty()); @@ -213,7 +213,7 @@ namespace rtl_tests { //STRA's type is 'consexpr const char*', function accepts 'string', //so type-casting in place as 'string' - auto [err, ret] = (*reverseString)(string(STRA)); + auto [err, ret] = reverseString->bind().call(string(STRA)); EXPECT_TRUE(err == rtl::error::None); ASSERT_FALSE(ret.isEmpty()); EXPECT_TRUE(ret.canViewAs()); @@ -232,7 +232,7 @@ namespace rtl_tests string retVal = ret.view()->get(); EXPECT_TRUE(retVal == STRB_REVERSE); } { - auto [err, ret] = (*reverseString)(); + auto [err, ret] = reverseString->bind().call(); EXPECT_TRUE(err == rtl::error::None); ASSERT_FALSE(ret.isEmpty()); EXPECT_TRUE(ret.canViewAs()); diff --git a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp index 8794ec85..d8236545 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupFunction.hpp @@ -13,12 +13,14 @@ #include -#include "cache_lambda_function.h" #include "cache_function_ptr.h" +#include "cache_lambda_function.h" #include "SetupFunction.h" #include "RObjectBuilder.hpp" +#include "FunctorId.hpp" + namespace rtl { namespace detail diff --git a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp index 2957d82b..52b1ee85 100644 --- a/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp +++ b/ReflectionTemplateLib/rtl/builder/SetupMethod.hpp @@ -18,10 +18,11 @@ #include "SetupMethod.h" #include "RObjectBuilder.hpp" -#include "lambda_method.h" +#include "cache_lambda_method.h" #include "cache_method_ptr.h" #include "cache_method_ptr_const.h" -#include "cache_lambda_method.h" + +#include "FunctorId.hpp" namespace rtl::detail { diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h index 4e3095fc..e7eccd61 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h @@ -35,7 +35,8 @@ namespace rtl::cache m_cache.push_back(dispatch::lambda_function(p_functor, erasure)); p_functor.m_lambda = &m_cache.back(); - (m_erasure_cache.back()).m_function = m_cache.back().template get_hopper(); + m_erasure_cache.back().m_function = m_cache.back().template get_hopper(); + return m_cache.back(); } diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h index 50e00856..f2582276 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h @@ -36,7 +36,7 @@ namespace rtl::cache m_cache.push_back(dispatch::lambda_method(p_functor, erasure)); p_functor.m_lambda = &m_cache.back(); - (m_erasure_cache.back()).m_method = m_cache.back().template get_hopper(); + m_erasure_cache.back().m_method = m_cache.back().template get_hopper(); return m_cache.back(); } diff --git a/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt b/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt index a4020ede..feb99088 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/detail/inc/CMakeLists.txt @@ -5,6 +5,7 @@ set(LOCAL_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/ConversionUtils.h" "${CMAKE_CURRENT_SOURCE_DIR}/CxxReflection.h" "${CMAKE_CURRENT_SOURCE_DIR}/FunctorId.h" + "${CMAKE_CURRENT_SOURCE_DIR}/FunctorId.hpp" "${CMAKE_CURRENT_SOURCE_DIR}/ReflectCast.h" "${CMAKE_CURRENT_SOURCE_DIR}/ReflectCast.hpp" "${CMAKE_CURRENT_SOURCE_DIR}/ReflectCastUtil.h" diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h index 2ec2e6c2..ab3453a9 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h @@ -13,8 +13,6 @@ #include "rtl_forward_decls.h" -#include "RObject.h" - namespace rtl::detail { template @@ -27,12 +25,6 @@ namespace rtl::detail template constexpr rtl::Return operator()(_args&&...params) const noexcept; - - template - constexpr rtl::error call_v(_args&&...) const noexcept; - - template - std::any call_r(_args&&...) const noexcept; }; } diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index b322b959..c967376b 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -38,33 +38,21 @@ namespace rtl::detail template template - constexpr inline rtl::Return FunctionCaller<_signature...>::operator()(_args&&...params) const noexcept - { - return call(std::forward<_args>(params)...); - } - - - template - template - constexpr error FunctionCaller<_signature...>::call_v(_args&& ...params) const noexcept + ForceInline constexpr Return FunctionCaller<_signature...>::operator()(_args&&...params) const noexcept { auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); - if (functorId) [[likely]] { - functorId->template get_lambda_function<_args...>()->m_erasure->void_hop(std::forward<_args>(params)...); - } - return error::None; - } - - - template - template - ForceInline std::any FunctionCaller<_signature...>::call_r(_args&& ...params) const noexcept - { - auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); - if (functorId) [[likely]] { - return functorId->template get_lambda_function<_args...>()->m_erasure->return_hop(std::forward<_args>(params)...); + if (functorId) [[likely]] + { + auto caller = functorId->template get_lambda_function<_args...>()->m_erasure; + if(functorId->m_lambda->is_void()) { + caller->void_hop(std::forward<_args>(params)...); + return {error::None, RObject{} }; + } + else { + return caller->return_hop(std::forward<_args>(params)...); + } } - return std::any(); + return {error::SignatureMismatch, RObject{} }; } } @@ -89,7 +77,7 @@ namespace rtl::detail template template inline constexpr const function<_returnType(_signature...)> - HopFunction<_signature...>::returnT() const + HopFunction<_signature...>::returnT() const { const auto retId = TypeId<_returnType>::get(); if (m_lambda != nullptr) [[likely]] { diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h index 2761736c..ce30dd96 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.h @@ -11,12 +11,7 @@ #pragma once -#include "rtl_typeid.h" -#include "rtl_constants.h" #include "rtl_forward_decls.h" -#include "lambda_method.h" -#include "lambda_function.h" - namespace rtl::detail { @@ -81,15 +76,15 @@ namespace rtl::detail } template - constexpr const dispatch::lambda_function<_signature...>* get_lambda_function(std::size_t p_argsId = 0) const - { - return m_lambda->to_function<_signature...>(p_argsId); - } + using lambda_ft = dispatch::lambda_function<_signature...>; + + template + using lambda_mt = dispatch::lambda_method; + + template + constexpr const lambda_ft* get_lambda_function(std::size_t p_argsId = 0) const; - template - constexpr const dispatch::lambda_method<_recordType, _signature...>* get_lambda_method(std::size_t p_recordId = 0, std::size_t p_argsId = 0) const - { - return m_lambda->to_method<_recordType, _signature...>(p_recordId, p_argsId); - } + template + constexpr const lambda_mt* get_lambda_method(std::size_t p_recordId = 0, std::size_t p_argsId = 0) const; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctorId.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.hpp new file mode 100644 index 00000000..5d81b100 --- /dev/null +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctorId.hpp @@ -0,0 +1,32 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "FunctorId.h" + +#include "lambda_method.h" +#include "lambda_function.h" + +namespace rtl::detail +{ + template + inline constexpr const FunctorId::lambda_ft* FunctorId::get_lambda_function(std::size_t p_argsId) const + { + return m_lambda->to_function(p_argsId); + } + + template + inline constexpr const FunctorId::lambda_mt* FunctorId::get_lambda_method(std::size_t p_recordId, std::size_t p_argsId) const + { + return m_lambda->to_method(p_recordId, p_argsId); + } +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h index 2e7f529e..7654618e 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h @@ -11,7 +11,8 @@ #pragma once -#include "erased_method.h" +#include "rtl_typeid.h" +#include "rtl_forward_decls.h" namespace rtl::detail { @@ -23,10 +24,7 @@ namespace rtl::detail const _recordType& m_target; template - constexpr error call_v(_args&&...params) const noexcept; - - template - std::any call_r(_args&&...params) const noexcept; + constexpr Return operator()(_args&&...params) const noexcept; }; } diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index 4c1dbb13..301c6128 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -15,6 +15,7 @@ #include "RObject.h" #include "MethodInvoker.h" #include "MethodContainer.h" +#include "erased_method.h" namespace rtl::detail { @@ -143,7 +144,7 @@ namespace rtl::detail return { error::NonConstOverloadMissing, RObject{} }; } // else the signature might be wrong. - return { error::SignatureMismatch , RObject{} }; + return { error::SignatureMismatch, RObject{} }; } } } @@ -171,7 +172,7 @@ namespace rtl::detail template template inline constexpr const method<_returnType(_recordType::*)(_signature...)> - HopMethod<_recordType, _signature...>::returnT() const + HopMethod<_recordType, _signature...>::returnT() const { if (m_lambda != nullptr) [[likely]] { @@ -187,23 +188,20 @@ namespace rtl::detail { template template - constexpr error ErasedInvoker<_recordType>::call_v(_args&&...params) const noexcept + ForceInline constexpr Return ErasedInvoker<_recordType>::operator()(_args&&...params) const noexcept { auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); - if (functorId) [[likely]] { - functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->void_hop(m_target, std::forward<_args>(params)...); - } - return error::None; - } - - template - template - ForceInline std::any ErasedInvoker<_recordType>::call_r(_args&&...params) const noexcept - { - auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); - if (functorId) [[likely]] { - return functorId->template get_lambda_method<_recordType, _args...>()->m_erasure->return_hop(m_target, std::forward<_args>(params)...); + if (functorId) [[likely]] + { + auto caller = functorId->template get_lambda_method<_recordType, _args...>()->m_erasure; + if(functorId->m_lambda->is_void()) { + caller->void_hop(m_target, std::forward<_args>(params)...); + return { error::None, RObject{} }; + } + else { + return caller->return_hop(m_target, std::forward<_args>(params)...); + } } - return std::any(); + return { error::SignatureMismatch, RObject{} }; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h b/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h index bb43306b..a5a9723c 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h @@ -12,11 +12,9 @@ #pragma once #include -#include #include #include "ReflectCast.h" -#include "rtl_forward_decls.h" #include "FunctorId.h" namespace rtl::detail diff --git a/ReflectionTemplateLib/rtl/detail/inc/RObjectUPtr.h b/ReflectionTemplateLib/rtl/detail/inc/RObjectUPtr.h index 1fd4ce58..4fe7c442 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/RObjectUPtr.h +++ b/ReflectionTemplateLib/rtl/detail/inc/RObjectUPtr.h @@ -13,9 +13,8 @@ #include #include #include -#include -#include "RObjectBuilder.hpp" +#include "RObject.h" /*------------------------------------------------------------------------------------------ RObjectUPtr @@ -70,13 +69,13 @@ namespace rtl::detail // Construct directly from std::unique_ptr, tracking RTL-owned heap allocations. RObjectUPtr(std::unique_ptr&& pUniquePtr) : m_uniquePtr(std::move(pUniquePtr)) { - RObject::getInstanceCounter().fetch_add(1, std::memory_order_relaxed); + RObject::getInstanceCounter()++;//.fetch_add(1, std::memory_order_relaxed); } // Destructor: decrements allocation count if we still own the object. ~RObjectUPtr() { if (m_uniquePtr) { - RObject::getInstanceCounter().fetch_sub(1, std::memory_order_relaxed); + RObject::getInstanceCounter()--;//.fetch_sub(1, std::memory_order_relaxed); } } @@ -87,7 +86,7 @@ namespace rtl::detail std::unique_ptr release() const { if (m_uniquePtr) { - RObject::getInstanceCounter().fetch_sub(1, std::memory_order_relaxed); + RObject::getInstanceCounter()--;//.fetch_sub(1, std::memory_order_relaxed); return std::move(m_uniquePtr); } return nullptr; diff --git a/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h b/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h index 104d1142..726ad21b 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h +++ b/ReflectionTemplateLib/rtl/detail/inc/ReflectCast.h @@ -31,7 +31,7 @@ namespace rtl::detail template class ReflectCast { - static std::vector>& conversions() { + ForceInline static std::vector>& conversions() { static std::vector> converters; return converters; } @@ -40,7 +40,7 @@ namespace rtl::detail template static void pushConversion(); - static const std::vector>& getConversions() { + ForceInline static const std::vector>& getConversions() { return conversions(); } }; diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index 06ec3000..15ec6e99 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -20,10 +20,13 @@ namespace rtl::dispatch { const functor& m_functor; + const bool m_is_void; + // protected: lambda_base(const functor& p_functor) noexcept - :m_functor(p_functor) + : m_functor(p_functor) + , m_is_void(p_functor.m_returnId == detail::TypeId::get()) { } template @@ -57,6 +60,10 @@ namespace rtl::dispatch GETTER_CREF(functor, _functor, m_functor); + constexpr bool is_void() const { + return m_is_void; + } + template constexpr bool is_returning() const { diff --git a/ReflectionTemplateLib/rtl/erasure/aware_function.h b/ReflectionTemplateLib/rtl/erasure/aware_function.h index b139055d..f8e93b2e 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_function.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_function.h @@ -11,8 +11,9 @@ #pragma once +#include "RObject.h" #include "erased_function.h" -#include "rtl_function.h" +#include "RObjectBuilder.hpp" namespace rtl::erase { @@ -40,21 +41,36 @@ namespace rtl::erase } } - ForceInline static std::any return_hop(const base_t* p_this, signature_ts&&...params) noexcept + + ForceInline static rtl::Return return_hop(const base_t* p_this, signature_ts&&...params) noexcept { if constexpr (!std::is_void_v) { auto this_p = static_cast(p_this); auto&& ret_v = this_p->m_function(std::forward(params)...); - if constexpr (std::is_reference_v) { - return std::any(&ret_v); + constexpr bool isConstCastSafe = (!traits::is_const_v); + + if constexpr (std::is_reference_v) + { + using T = traits::raw_t; + return{ error::None, + detail::RObjectBuilder::template build ( + &ret_v, std::nullopt, isConstCastSafe + ) + }; } - else { - return std::any(std::forward(ret_v)); + else + { + using T = std::remove_cvref_t; + return{ error::None, + detail::RObjectBuilder::template build ( + std::forward(ret_v), std::nullopt, isConstCastSafe + ) + }; } } - else return std::any(); + return {error::SignatureMismatch, RObject{ }}; } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/aware_method.h b/ReflectionTemplateLib/rtl/erasure/aware_method.h index 784cfb65..86a5516b 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_method.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_method.h @@ -12,6 +12,7 @@ #pragma once #include "erased_method.h" +#include "RObjectBuilder.hpp" namespace rtl::erase { @@ -39,21 +40,34 @@ namespace rtl::erase } } - ForceInline static std::any return_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept + ForceInline static rtl::Return return_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept { if constexpr (!std::is_void_v) { auto this_p = static_cast(p_this); auto&& ret_v = this_p->m_method(const_cast(p_target), std::forward(params)...); + constexpr bool isConstCastSafe = (!traits::is_const_v); - if constexpr (std::is_reference_v) { - return std::any(&ret_v); + if constexpr (std::is_reference_v) + { + using T = traits::raw_t; + return{ error::None, + detail::RObjectBuilder::template build ( + &ret_v, std::nullopt, isConstCastSafe + ) + }; } - else { - return std::any(std::forward(ret_v)); + else + { + using T = std::remove_cvref_t; + return{ error::None, + detail::RObjectBuilder::template build ( + std::forward(ret_v), std::nullopt, isConstCastSafe + ) + }; } } - else return std::any(); + return {error::SignatureMismatch, RObject{ }}; } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/aware_method_const.h b/ReflectionTemplateLib/rtl/erasure/aware_method_const.h index 5caedf3a..0d669649 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_method_const.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_method_const.h @@ -11,7 +11,9 @@ #pragma once +#include "RObject.h" #include "erased_method.h" +#include "RObjectBuilder.hpp" namespace rtl::erase { @@ -39,21 +41,34 @@ namespace rtl::erase } } - ForceInline static std::any return_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept + ForceInline static rtl::Return return_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept { if constexpr (!std::is_void_v) { auto this_p = static_cast(p_this); auto&& ret_v = this_p->m_method(p_target, std::forward(params)...); + constexpr bool isConstCastSafe = (!traits::is_const_v); - if constexpr (std::is_reference_v) { - return std::any(&ret_v); + if constexpr (std::is_reference_v) + { + using T = traits::raw_t; + return{ error::None, + detail::RObjectBuilder::template build ( + &ret_v, std::nullopt, isConstCastSafe + ) + }; } - else { - return std::any(std::forward(ret_v)); + else + { + using T = std::remove_cvref_t; + return{ error::None, + detail::RObjectBuilder::template build ( + std::forward(ret_v), std::nullopt, isConstCastSafe + ) + }; } } - else return std::any(); + return {error::SignatureMismatch, RObject{ }}; } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erased_function.h b/ReflectionTemplateLib/rtl/erasure/erased_function.h index 30050564..9e535d08 100644 --- a/ReflectionTemplateLib/rtl/erasure/erased_function.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_function.h @@ -11,7 +11,6 @@ #pragma once -#include #include "rtl_forward_decls.h" namespace rtl::erase @@ -24,7 +23,7 @@ namespace rtl::erase (*hop_void)(this, std::forward(params)...); } - ForceInline std::any return_hop(signature_ts&&...params) const noexcept + ForceInline rtl::Return return_hop(signature_ts&&...params) const noexcept { return (*hop_return)(this, std::forward(params)...); } @@ -35,7 +34,7 @@ namespace rtl::erase using functor_vt = void(*)(const this_t*, signature_ts&&...); - using functor_rt = std::any(*)(const this_t*, signature_ts&&...); + using functor_rt = rtl::Return(*)(const this_t*, signature_ts&&...); functor_vt hop_void = nullptr; diff --git a/ReflectionTemplateLib/rtl/erasure/erased_method.h b/ReflectionTemplateLib/rtl/erasure/erased_method.h index 56050586..16da0582 100644 --- a/ReflectionTemplateLib/rtl/erasure/erased_method.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_method.h @@ -11,7 +11,6 @@ #pragma once -#include #include "rtl_forward_decls.h" namespace rtl::erase @@ -24,7 +23,7 @@ namespace rtl::erase (*hop_void)(this, p_target, std::forward(params)...); } - ForceInline std::any return_hop(const record_t& p_target, signature_ts&&...params) const noexcept + ForceInline rtl::Return return_hop(const record_t& p_target, signature_ts&&...params) const noexcept { return (*hop_return)(this, p_target, std::forward(params)...); } @@ -35,7 +34,7 @@ namespace rtl::erase using functor_vt = void(*)(const this_t*, const record_t&, signature_ts&&...); - using functor_rt = std::any(*)(const this_t*, const record_t&, signature_ts&&...); + using functor_rt = rtl::Return(*)(const this_t*, const record_t&, signature_ts&&...); functor_vt hop_void = nullptr; diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 97822e37..6edd8c0d 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -14,14 +14,8 @@ #include #include #include -#include -#include "FunctorId.h" -#include "RObject.h" -#include "rtl_constants.h" #include "FunctionCaller.h" -#include "lambda_function.h" -#include "rtl_errors.h" namespace rtl { @@ -102,7 +96,7 @@ namespace rtl { bool hasSignature() const; template - Return operator()(_args&&...params) const noexcept; + constexpr const detail::FunctionCaller<_args...> operator()(_args&&...params) const noexcept; template constexpr const detail::FunctionCaller<_signature...> bind() const noexcept; diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index e728d6c4..77dd5ec1 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -51,9 +51,9 @@ namespace rtl * if the arguments did not match with any overload, returns RObject with error::SignatureMismatch * providing optional syntax, Function::call() does the exact same thing. */ template - inline Return Function::operator()(_args&& ...params) const noexcept + inline constexpr const detail::FunctionCaller<_args...> Function::operator()(_args&& ...params) const noexcept { - return detail::FunctionCaller<>{ this }.call(std::forward<_args>(params)...); + return detail::FunctionCaller<_args...>{ this }; } diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index f4249ca5..d298fb60 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -16,7 +16,6 @@ #include "RObject.h" #include "Function.h" #include "MethodInvoker.h" -#include "lambda_method.h" namespace rtl { @@ -70,7 +69,7 @@ namespace rtl { const detail::NonConstInvoker<_signature...> bind(constCast&& pTarget) const; template - constexpr detail::ErasedInvoker<_recordType> operator()(const _recordType& pTarget) const + constexpr const detail::ErasedInvoker<_recordType> operator()(const _recordType& pTarget) const { return detail::ErasedInvoker<_recordType>{ (*this), pTarget }; } diff --git a/ReflectionTemplateLib/rtl/inc/RObject.h b/ReflectionTemplateLib/rtl/inc/RObject.h index 4e89d6f7..8e5daa38 100644 --- a/ReflectionTemplateLib/rtl/inc/RObject.h +++ b/ReflectionTemplateLib/rtl/inc/RObject.h @@ -11,7 +11,8 @@ #pragma once -#include +//#include +#include #include "view.h" #include "RObjectId.h" @@ -89,7 +90,11 @@ namespace rtl template, int> = 0> std::optional> view() const noexcept; - static std::atomic& getInstanceCounter(); + static std::size_t& /*std::atomic&*/ getInstanceCounter() + { + static std::size_t/*std::atomic*/ instanceCounter = {0}; + return instanceCounter; + } //friends :) friend CxxMirror; diff --git a/ReflectionTemplateLib/rtl/inc/RObject.hpp b/ReflectionTemplateLib/rtl/inc/RObject.hpp index 35802478..85a86213 100644 --- a/ReflectionTemplateLib/rtl/inc/RObject.hpp +++ b/ReflectionTemplateLib/rtl/inc/RObject.hpp @@ -59,13 +59,7 @@ namespace rtl pOther.m_converters = nullptr; return *this; } - - inline std::atomic& RObject::getInstanceCounter() - { - static std::atomic instanceCounter = {0}; - return instanceCounter; - } - + inline std::size_t RObject::getConverterIndex(const std::size_t pToTypeId) const { diff --git a/ReflectionTemplateLib/rtl/rtl_forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h index 228a29dd..13c690be 100644 --- a/ReflectionTemplateLib/rtl/rtl_forward_decls.h +++ b/ReflectionTemplateLib/rtl/rtl_forward_decls.h @@ -31,7 +31,7 @@ namespace rtl template struct method; - namespace erase + namespace erase { template struct erased_function; diff --git a/ReflectionTemplateLib/rtl/src/CxxMirror.cpp b/ReflectionTemplateLib/rtl/src/CxxMirror.cpp index e75c71f4..3b3f21e8 100644 --- a/ReflectionTemplateLib/rtl/src/CxxMirror.cpp +++ b/ReflectionTemplateLib/rtl/src/CxxMirror.cpp @@ -8,7 +8,7 @@ * * *************************************************************************/ - +#include #include "RObject.h" #include "CxxMirror.h" diff --git a/ReflectionTemplateLib/rtl/src/Function.cpp b/ReflectionTemplateLib/rtl/src/Function.cpp index ad1109c9..94db0f1c 100644 --- a/ReflectionTemplateLib/rtl/src/Function.cpp +++ b/ReflectionTemplateLib/rtl/src/Function.cpp @@ -12,6 +12,7 @@ #include #include "Function.h" +#include "FunctorId.h" namespace rtl { From d73a85fc4913f1b741be3143f43456f493d210aa Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Tue, 30 Sep 2025 23:02:13 +0530 Subject: [PATCH 51/58] type-erased return value optimized. --- .../rtl/builder/RObjectBuilder.hpp | 10 ++-- .../rtl/builder/RecordBuilder.h | 2 +- .../rtl/builder/RecordBuilder.hpp | 4 +- .../rtl/detail/inc/FunctionCaller.hpp | 17 +++--- .../rtl/detail/inc/MethodInvoker.hpp | 23 ++++---- .../rtl/detail/inc/RObjectId.h | 2 +- .../rtl/erasure/aware_function.h | 51 +++++++----------- .../rtl/erasure/aware_method.h | 51 ++++++++---------- .../rtl/erasure/aware_method_const.h | 52 ++++++++----------- .../rtl/erasure/erased_function.h | 18 +++---- .../rtl/erasure/erased_method.h | 17 +++--- ReflectionTemplateLib/rtl/inc/RObject.h | 6 +++ ReflectionTemplateLib/rtl/rtl_forward_decls.h | 6 +++ ReflectionTemplateLib/rtl/rtl_traits.h | 4 +- 14 files changed, 118 insertions(+), 145 deletions(-) diff --git a/ReflectionTemplateLib/rtl/builder/RObjectBuilder.hpp b/ReflectionTemplateLib/rtl/builder/RObjectBuilder.hpp index 1504f405..e7b4cd91 100644 --- a/ReflectionTemplateLib/rtl/builder/RObjectBuilder.hpp +++ b/ReflectionTemplateLib/rtl/builder/RObjectBuilder.hpp @@ -39,7 +39,7 @@ namespace rtl::detail std::in_place_type>, RObjectUPtr<_T>(std::unique_ptr<_T>(static_cast<_T*>(pVal))) }, - RObjectId::create, alloc::Heap>(pClonerId, pIsConstCastSafe), + RObjectId::create, alloc::Heap>(pIsConstCastSafe, pClonerId), &getConverters>()); } @@ -49,12 +49,12 @@ namespace rtl::detail ForceInline RObject RObjectBuilder::build(T&& pVal, std::optional pClonerId, bool pIsConstCastSafe) noexcept { using _T = traits::raw_t; - constexpr bool isRawPointer = std::is_pointer_v>; + constexpr bool isRawPointer = std::is_pointer_v>; if constexpr (isRawPointer) { return RObject( std::any { static_cast(pVal) }, - RObjectId::create(pClonerId, pIsConstCastSafe), + RObjectId::create(pIsConstCastSafe, pClonerId), &getConverters() ); } else @@ -66,7 +66,7 @@ namespace rtl::detail std::in_place_type>, RObjectUPtr(std::move(pVal)) }, - RObjectId::create(pClonerId, pIsConstCastSafe), + RObjectId::create(pIsConstCastSafe, pClonerId), &getConverters() ); } else @@ -76,7 +76,7 @@ namespace rtl::detail std::in_place_type, std::forward(pVal) }, - RObjectId::create(pClonerId, pIsConstCastSafe), + RObjectId::create(pIsConstCastSafe, pClonerId), &getConverters() ); } } diff --git a/ReflectionTemplateLib/rtl/builder/RecordBuilder.h b/ReflectionTemplateLib/rtl/builder/RecordBuilder.h index da6db803..7f28bd76 100644 --- a/ReflectionTemplateLib/rtl/builder/RecordBuilder.h +++ b/ReflectionTemplateLib/rtl/builder/RecordBuilder.h @@ -62,7 +62,7 @@ namespace rtl { const Builder methodStatic(const std::string_view pFunction) const; template - constexpr const ConstructorBuilder<_recordType, traits::remove_const_n_ref_t<_signature>...> constructor() const; + constexpr const ConstructorBuilder<_recordType, traits::remove_cref_t<_signature>...> constructor() const; }; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/builder/RecordBuilder.hpp b/ReflectionTemplateLib/rtl/builder/RecordBuilder.hpp index b05f5b0b..b9a74cf6 100644 --- a/ReflectionTemplateLib/rtl/builder/RecordBuilder.hpp +++ b/ReflectionTemplateLib/rtl/builder/RecordBuilder.hpp @@ -41,7 +41,7 @@ namespace rtl::builder * template params <...> - any combination of parameters. */ template template - inline constexpr const ConstructorBuilder<_recordType, traits::remove_const_n_ref_t<_signature>...> MethodBuilder<_recordType>::constructor() const + inline constexpr const ConstructorBuilder<_recordType, traits::remove_cref_t<_signature>...> MethodBuilder<_recordType>::constructor() const { constexpr bool isDefaultCtor = (sizeof...(_signature) == 0); constexpr bool isCopyOrMoveCtor = (sizeof...(_signature) == 1 && traits::is_first_type_same_v<_recordType, _signature...>); @@ -51,7 +51,7 @@ namespace rtl::builder static_assert(!isCopyOrMoveCtor, "Copy/Move-constructor registration detected! It is implicitly registered with the Type."); static_assert(isDeclearedCtor, "Constructor with given signature is not valid or declearation not found."); - return ConstructorBuilder<_recordType, traits::remove_const_n_ref_t<_signature>...>(); + return ConstructorBuilder<_recordType, traits::remove_cref_t<_signature>...>(); } diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index c967376b..5b89a0c7 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -43,16 +43,17 @@ namespace rtl::detail auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { + RObject robject; + auto caller = functorId->template get_lambda_function<_args...>()->m_erasure; - if(functorId->m_lambda->is_void()) { - caller->void_hop(std::forward<_args>(params)...); - return {error::None, RObject{} }; - } - else { - return caller->return_hop(std::forward<_args>(params)...); - } + + caller->hop(robject.m_object, std::forward<_args>(params)...); + + robject.m_objectId = caller->get_robject_id(); + + return { error::None, robject }; } - return {error::SignatureMismatch, RObject{} }; + else return {error::SignatureMismatch, RObject{} }; } } diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index 301c6128..f8b5d5ce 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -43,7 +43,7 @@ namespace rtl::detail { if constexpr (sizeof...(_signature) == 0) { // executes when bind doesn't have any explicit signature types specified. (e.g. perfect-forwaring) - return Invoker...>::invoke(*m_method, *m_target, std::forward<_args>(params)...); + return Invoker...>::invoke(*m_method, *m_target, std::forward<_args>(params)...); } else { return Invoker<_signature...>::invoke(*m_method, *m_target, std::forward<_args>(params)...); @@ -110,7 +110,7 @@ namespace rtl::detail else [[likely]] { if constexpr (sizeof...(_signature) == 0) { - return Invoker...>::invoke(*m_method, *m_target, std::forward<_args>(params)...); + return Invoker...>::invoke(*m_method, *m_target, std::forward<_args>(params)...); } else { return Invoker<_signature...>::invoke(*m_method, *m_target, std::forward<_args>(params)...); @@ -191,17 +191,18 @@ namespace rtl::detail ForceInline constexpr Return ErasedInvoker<_recordType>::operator()(_args&&...params) const noexcept { auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); - if (functorId) [[likely]] + if (functorId) [[likely]] { + RObject robject; + auto caller = functorId->template get_lambda_method<_recordType, _args...>()->m_erasure; - if(functorId->m_lambda->is_void()) { - caller->void_hop(m_target, std::forward<_args>(params)...); - return { error::None, RObject{} }; - } - else { - return caller->return_hop(m_target, std::forward<_args>(params)...); - } + + caller->hop(robject.m_object, m_target, std::forward<_args>(params)...); + + robject.m_objectId = caller->get_robject_id(); + + return { error::None, robject }; } - return { error::SignatureMismatch, RObject{} }; + else return { error::SignatureMismatch, RObject{} }; } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h b/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h index a5a9723c..3dd82196 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h +++ b/ReflectionTemplateLib/rtl/detail/inc/RObjectId.h @@ -57,7 +57,7 @@ namespace rtl::detail template - ForceInline static RObjectId create(std::optional pClonerId, bool pIsConstCastSafe) noexcept + ForceInline static RObjectId create(bool pIsConstCastSafe, std::optional pClonerId = std::nullopt) noexcept { // extract wrapper info. using _W = traits::std_wrapper>; diff --git a/ReflectionTemplateLib/rtl/erasure/aware_function.h b/ReflectionTemplateLib/rtl/erasure/aware_function.h index f8e93b2e..9b5c1ae2 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_function.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_function.h @@ -11,9 +11,7 @@ #pragma once -#include "RObject.h" #include "erased_function.h" -#include "RObjectBuilder.hpp" namespace rtl::erase { @@ -28,49 +26,38 @@ namespace rtl::erase aware_function() { - base_t::hop_void = void_hop; - base_t::hop_return = return_hop; + constexpr bool isConstCastSafe = (!traits::is_const_v); + + base_t::hopper = hopper; + base_t::robj_id = detail::RObjectId::create(isConstCastSafe); } - constexpr static void void_hop(const base_t* p_this, signature_ts&&...params) noexcept + constexpr static void hopper(const base_t* p_this, std::optional& p_return, signature_ts&&...params) noexcept { - if constexpr (std::is_void_v) - { - auto this_p = static_cast(p_this); + auto this_p = static_cast(p_this); + + if constexpr (std::is_void_v) { this_p->m_function(std::forward(params)...); } - } - - - ForceInline static rtl::Return return_hop(const base_t* p_this, signature_ts&&...params) noexcept - { - if constexpr (!std::is_void_v) - { - auto this_p = static_cast(p_this); + else { auto&& ret_v = this_p->m_function(std::forward(params)...); - constexpr bool isConstCastSafe = (!traits::is_const_v); - - if constexpr (std::is_reference_v) + if constexpr (std::is_pointer_v) + { + using raw_t = std::remove_pointer_t; + p_return.emplace(static_cast(ret_v)); + } + else if constexpr (std::is_reference_v) { - using T = traits::raw_t; - return{ error::None, - detail::RObjectBuilder::template build ( - &ret_v, std::nullopt, isConstCastSafe - ) - }; + using raw_t = std::remove_cv_t>; + p_return.emplace(static_cast(&ret_v)); } else { - using T = std::remove_cvref_t; - return{ error::None, - detail::RObjectBuilder::template build ( - std::forward(ret_v), std::nullopt, isConstCastSafe - ) - }; + using rconst_t = std::add_const_t>; + p_return.emplace(rconst_t(std::forward(ret_v))); } } - return {error::SignatureMismatch, RObject{ }}; } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/aware_method.h b/ReflectionTemplateLib/rtl/erasure/aware_method.h index 86a5516b..a2b02483 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_method.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_method.h @@ -11,8 +11,8 @@ #pragma once +#include "RObjectId.h" #include "erased_method.h" -#include "RObjectBuilder.hpp" namespace rtl::erase { @@ -27,47 +27,38 @@ namespace rtl::erase aware_method() { - base_t::hop_void = void_hop; - base_t::hop_return = return_hop; + constexpr bool isConstCastSafe = (!traits::is_const_v); + + base_t::hopper = hopper; + base_t::robj_id = detail::RObjectId::create(isConstCastSafe); } - constexpr static void void_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept + constexpr static void hopper(const base_t* p_this, std::optional& p_return, const record_t& p_target, signature_ts&&...params) noexcept { - if constexpr (std::is_void_v) - { - auto this_p = static_cast(p_this); + auto this_p = static_cast(p_this); + + if constexpr (std::is_void_v) { this_p->m_method(const_cast(p_target), std::forward(params)...); } - } - - ForceInline static rtl::Return return_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept - { - if constexpr (!std::is_void_v) - { - auto this_p = static_cast(p_this); + else { auto&& ret_v = this_p->m_method(const_cast(p_target), std::forward(params)...); - constexpr bool isConstCastSafe = (!traits::is_const_v); - if constexpr (std::is_reference_v) + if constexpr (std::is_pointer_v) + { + using raw_t = std::remove_pointer_t; + p_return.emplace(static_cast(ret_v)); + } + else if constexpr (std::is_reference_v) { - using T = traits::raw_t; - return{ error::None, - detail::RObjectBuilder::template build ( - &ret_v, std::nullopt, isConstCastSafe - ) - }; + using raw_t = std::remove_cv_t>; + p_return.emplace(static_cast(&ret_v)); } - else + else { - using T = std::remove_cvref_t; - return{ error::None, - detail::RObjectBuilder::template build ( - std::forward(ret_v), std::nullopt, isConstCastSafe - ) - }; + using rconst_t = std::add_const_t>; + p_return.emplace(rconst_t(std::forward(ret_v))); } } - return {error::SignatureMismatch, RObject{ }}; } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/aware_method_const.h b/ReflectionTemplateLib/rtl/erasure/aware_method_const.h index 0d669649..6c02f0af 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_method_const.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_method_const.h @@ -11,9 +11,8 @@ #pragma once -#include "RObject.h" +#include "RObjectId.h" #include "erased_method.h" -#include "RObjectBuilder.hpp" namespace rtl::erase { @@ -28,47 +27,38 @@ namespace rtl::erase aware_method() { - base_t::v_hop = void_hop; - base_t::r_hop = return_hop; + constexpr bool isConstCastSafe = (!traits::is_const_v); + + base_t::hopper = hopper; + base_t::robj_id = detail::RObjectId::create(isConstCastSafe); } - constexpr static void void_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept + constexpr static void hopper(const base_t* p_this, std::optional& p_return, const record_t& p_target, signature_ts&&...params) noexcept { - if constexpr (std::is_void_v) - { - auto this_p = static_cast(p_this); + auto this_p = static_cast(p_this); + + if constexpr (std::is_void_v) { this_p->m_method(p_target, std::forward(params)...); } - } - - ForceInline static rtl::Return return_hop(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept - { - if constexpr (!std::is_void_v) - { - auto this_p = static_cast(p_this); + else { auto&& ret_v = this_p->m_method(p_target, std::forward(params)...); - constexpr bool isConstCastSafe = (!traits::is_const_v); - if constexpr (std::is_reference_v) + if constexpr (std::is_pointer_v) + { + using raw_t = std::remove_pointer_t; + p_return.emplace(static_cast(ret_v)); + } + else if constexpr (std::is_reference_v) { - using T = traits::raw_t; - return{ error::None, - detail::RObjectBuilder::template build ( - &ret_v, std::nullopt, isConstCastSafe - ) - }; + using raw_t = std::remove_cv_t>; + p_return.emplace(static_cast(&ret_v)); } - else + else { - using T = std::remove_cvref_t; - return{ error::None, - detail::RObjectBuilder::template build ( - std::forward(ret_v), std::nullopt, isConstCastSafe - ) - }; + using rconst_t = std::add_const_t>; + p_return.emplace(rconst_t(std::forward(ret_v))); } } - return {error::SignatureMismatch, RObject{ }}; } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erased_function.h b/ReflectionTemplateLib/rtl/erasure/erased_function.h index 9e535d08..f0c6cb0c 100644 --- a/ReflectionTemplateLib/rtl/erasure/erased_function.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_function.h @@ -11,6 +11,7 @@ #pragma once +#include "RObjectId.h" #include "rtl_forward_decls.h" namespace rtl::erase @@ -18,26 +19,21 @@ namespace rtl::erase template struct erased_function { - constexpr void void_hop(signature_ts&&...params) const noexcept + constexpr void hop(std::optional& p_return, signature_ts&&...params) const noexcept { - (*hop_void)(this, std::forward(params)...); + (*hopper)(this, p_return, std::forward(params)...); } - ForceInline rtl::Return return_hop(signature_ts&&...params) const noexcept - { - return (*hop_return)(this, std::forward(params)...); - } + GETTER(detail::RObjectId, _robject_id, robj_id); protected: using this_t = erased_function; - using functor_vt = void(*)(const this_t*, signature_ts&&...); - - using functor_rt = rtl::Return(*)(const this_t*, signature_ts&&...); + using functor_t = void(*)(const this_t*, std::optional&, signature_ts&&...); - functor_vt hop_void = nullptr; + functor_t hopper = nullptr; - functor_rt hop_return = nullptr; + detail::RObjectId robj_id; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erased_method.h b/ReflectionTemplateLib/rtl/erasure/erased_method.h index 16da0582..507e1e4d 100644 --- a/ReflectionTemplateLib/rtl/erasure/erased_method.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_method.h @@ -18,26 +18,21 @@ namespace rtl::erase template struct erased_method { - constexpr void void_hop(const record_t& p_target, signature_ts&&...params) const noexcept + constexpr void hop(std::optional& p_return, const record_t& p_target, signature_ts&&...params) const noexcept { - (*hop_void)(this, p_target, std::forward(params)...); + (*hopper)(this, p_return, p_target, std::forward(params)...); } - ForceInline rtl::Return return_hop(const record_t& p_target, signature_ts&&...params) const noexcept - { - return (*hop_return)(this, p_target, std::forward(params)...); - } + GETTER(detail::RObjectId, _robject_id, robj_id); protected: using this_t = erased_method; - using functor_vt = void(*)(const this_t*, const record_t&, signature_ts&&...); - - using functor_rt = rtl::Return(*)(const this_t*, const record_t&, signature_ts&&...); + using functor_t = void(*)(const this_t*, std::optional& , const record_t&, signature_ts&&...); - functor_vt hop_void = nullptr; + functor_t hopper = nullptr; - functor_rt hop_return = nullptr; + detail::RObjectId robj_id; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/RObject.h b/ReflectionTemplateLib/rtl/inc/RObject.h index 8e5daa38..26562732 100644 --- a/ReflectionTemplateLib/rtl/inc/RObject.h +++ b/ReflectionTemplateLib/rtl/inc/RObject.h @@ -105,6 +105,12 @@ namespace rtl template friend struct detail::RObjectBuilder; + + template + friend struct detail::FunctionCaller; + + template + friend struct detail::ErasedInvoker; }; struct [[nodiscard]] Return { diff --git a/ReflectionTemplateLib/rtl/rtl_forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h index 13c690be..08b1f8ac 100644 --- a/ReflectionTemplateLib/rtl/rtl_forward_decls.h +++ b/ReflectionTemplateLib/rtl/rtl_forward_decls.h @@ -53,6 +53,12 @@ namespace rtl template class FunctorContainer; + template + struct FunctionCaller; + + template + struct ErasedInvoker; + template class SetupMethod; diff --git a/ReflectionTemplateLib/rtl/rtl_traits.h b/ReflectionTemplateLib/rtl/rtl_traits.h index 0bef3cda..e1a53809 100644 --- a/ReflectionTemplateLib/rtl/rtl_traits.h +++ b/ReflectionTemplateLib/rtl/rtl_traits.h @@ -44,7 +44,7 @@ namespace rtl // Utility: Remove const and reference qualifiers from T. template - using remove_const_n_ref_t = std::remove_const_t>; + using remove_cref_t = std::remove_const_t>; // Utility: Remove const from T if T is not a reference; otherwise, leave as is. template @@ -55,7 +55,7 @@ namespace rtl using remove_const_n_ref_n_ptr = std::remove_const_t>>>; template - inline constexpr bool is_raw_ptr_v = std::is_pointer_v>; + inline constexpr bool is_raw_ptr_v = std::is_pointer_v>; template inline constexpr bool is_const_v = (std::is_const_v> || (std::is_pointer_v && std::is_const_v>)); From e3949213f54431e96fad1533fa58ad911eabe71b Mon Sep 17 00:00:00 2001 From: neeraj Date: Wed, 1 Oct 2025 01:11:08 +0530 Subject: [PATCH 52/58] refined erased return-type design. --- .../rtl/detail/inc/FunctionCaller.hpp | 22 ++++++++------ .../rtl/detail/inc/MethodInvoker.hpp | 20 ++++++++----- .../rtl/erasure/aware_function.h | 29 ++++++++++++------- .../rtl/erasure/aware_method.h | 28 +++++++++++------- .../rtl/erasure/erased_function.h | 18 +++++++++--- .../rtl/erasure/erased_method.h | 19 +++++++++--- ReflectionTemplateLib/rtl/inc/RObject.h | 2 +- ReflectionTemplateLib/rtl/inc/RObject.hpp | 2 +- 8 files changed, 93 insertions(+), 47 deletions(-) diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index 5b89a0c7..c662b825 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -43,17 +43,21 @@ namespace rtl::detail auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { - RObject robject; - auto caller = functorId->template get_lambda_function<_args...>()->m_erasure; - - caller->hop(robject.m_object, std::forward<_args>(params)...); - - robject.m_objectId = caller->get_robject_id(); - - return { error::None, robject }; + if(functorId->m_lambda->is_void()) + { + caller->hop_v(std::forward<_args>(params)...); + return { error::None, RObject{} }; + } + else + { + return{ error::None, + RObject{ caller->hop_r(std::forward<_args>(params)...), + caller->get_robject_id(), nullptr } + }; + } } - else return {error::SignatureMismatch, RObject{} }; + else return { error::SignatureMismatch, RObject{} }; } } diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index f8b5d5ce..0135bf47 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -193,15 +193,19 @@ namespace rtl::detail auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { - RObject robject; - auto caller = functorId->template get_lambda_method<_recordType, _args...>()->m_erasure; - - caller->hop(robject.m_object, m_target, std::forward<_args>(params)...); - - robject.m_objectId = caller->get_robject_id(); - - return { error::None, robject }; + if(functorId->m_lambda->is_void()) + { + caller->hop_v(m_target, std::forward<_args>(params)...); + return { error::None, RObject{} }; + } + else + { + return{ error::None, + RObject{ caller->hop_r(m_target, std::forward<_args>(params)...), + caller->get_robject_id(), nullptr } + }; + } } else return { error::SignatureMismatch, RObject{} }; } diff --git a/ReflectionTemplateLib/rtl/erasure/aware_function.h b/ReflectionTemplateLib/rtl/erasure/aware_function.h index 9b5c1ae2..80a3282d 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_function.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_function.h @@ -11,7 +11,9 @@ #pragma once +#include #include "erased_function.h" +#include "rtl_constants.h" namespace rtl::erase { @@ -28,36 +30,43 @@ namespace rtl::erase { constexpr bool isConstCastSafe = (!traits::is_const_v); - base_t::hopper = hopper; + base_t::hopper_v = hop_v; + base_t::hopper_r = hop_r; base_t::robj_id = detail::RObjectId::create(isConstCastSafe); } - constexpr static void hopper(const base_t* p_this, std::optional& p_return, signature_ts&&...params) noexcept + constexpr static void hop_v(const base_t* p_this, signature_ts&&...params) noexcept { - auto this_p = static_cast(p_this); - - if constexpr (std::is_void_v) { + if constexpr (std::is_void_v) + { + auto this_p = static_cast(p_this); this_p->m_function(std::forward(params)...); } - else { - auto&& ret_v = this_p->m_function(std::forward(params)...); + } + ForceInline static std::any hop_r(const base_t* p_this, signature_ts&&...params) noexcept + { + auto this_p = static_cast(p_this); + if constexpr (!std::is_void_v) + { + auto&& ret_v = this_p->m_function(std::forward(params)...); if constexpr (std::is_pointer_v) { using raw_t = std::remove_pointer_t; - p_return.emplace(static_cast(ret_v)); + return std::any(static_cast(ret_v)); } else if constexpr (std::is_reference_v) { using raw_t = std::remove_cv_t>; - p_return.emplace(static_cast(&ret_v)); + return std::any(static_cast(&ret_v)); } else { using rconst_t = std::add_const_t>; - p_return.emplace(rconst_t(std::forward(ret_v))); + return std::any(rconst_t(std::forward(ret_v))); } } + else return std::any(); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/aware_method.h b/ReflectionTemplateLib/rtl/erasure/aware_method.h index a2b02483..6eee7ce6 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_method.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_method.h @@ -13,6 +13,7 @@ #include "RObjectId.h" #include "erased_method.h" +#include namespace rtl::erase { @@ -29,36 +30,43 @@ namespace rtl::erase { constexpr bool isConstCastSafe = (!traits::is_const_v); - base_t::hopper = hopper; + base_t::hopper_v = hop_v; + base_t::hopper_r = hop_r; base_t::robj_id = detail::RObjectId::create(isConstCastSafe); } - constexpr static void hopper(const base_t* p_this, std::optional& p_return, const record_t& p_target, signature_ts&&...params) noexcept + constexpr static void hop_v(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept { - auto this_p = static_cast(p_this); - - if constexpr (std::is_void_v) { + if constexpr (std::is_void_v) + { + auto this_p = static_cast(p_this); this_p->m_method(const_cast(p_target), std::forward(params)...); } - else { - auto&& ret_v = this_p->m_method(const_cast(p_target), std::forward(params)...); + } + ForceInline static std::any hop_r(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept + { + if constexpr (!std::is_void_v) + { + auto this_p = static_cast(p_this); + auto&& ret_v = this_p->m_method(const_cast(p_target), std::forward(params)...); if constexpr (std::is_pointer_v) { using raw_t = std::remove_pointer_t; - p_return.emplace(static_cast(ret_v)); + return std::any(static_cast(ret_v)); } else if constexpr (std::is_reference_v) { using raw_t = std::remove_cv_t>; - p_return.emplace(static_cast(&ret_v)); + return std::any(static_cast(&ret_v)); } else { using rconst_t = std::add_const_t>; - p_return.emplace(rconst_t(std::forward(ret_v))); + return std::any(rconst_t(std::forward(ret_v))); } } + else return std::any(); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erased_function.h b/ReflectionTemplateLib/rtl/erasure/erased_function.h index f0c6cb0c..08a76e03 100644 --- a/ReflectionTemplateLib/rtl/erasure/erased_function.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_function.h @@ -13,15 +13,21 @@ #include "RObjectId.h" #include "rtl_forward_decls.h" +#include "rtl_typeid.h" namespace rtl::erase { template struct erased_function { - constexpr void hop(std::optional& p_return, signature_ts&&...params) const noexcept + constexpr void hop_v(signature_ts&&...params) const noexcept { - (*hopper)(this, p_return, std::forward(params)...); + (*hopper_v)(this, std::forward(params)...); + } + + ForceInline std::any hop_r(signature_ts&&...params) const noexcept + { + return (*hopper_r)(this, std::forward(params)...); } GETTER(detail::RObjectId, _robject_id, robj_id); @@ -30,9 +36,13 @@ namespace rtl::erase using this_t = erased_function; - using functor_t = void(*)(const this_t*, std::optional&, signature_ts&&...); + using functor_vt = void(*)(const this_t*, signature_ts&&...); + + using functor_rt = std::any(*)(const this_t*, signature_ts&&...); + + functor_vt hopper_v = nullptr; - functor_t hopper = nullptr; + functor_rt hopper_r = nullptr; detail::RObjectId robj_id; }; diff --git a/ReflectionTemplateLib/rtl/erasure/erased_method.h b/ReflectionTemplateLib/rtl/erasure/erased_method.h index 507e1e4d..2a725312 100644 --- a/ReflectionTemplateLib/rtl/erasure/erased_method.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_method.h @@ -11,6 +11,8 @@ #pragma once +#include +#include "RObjectId.h" #include "rtl_forward_decls.h" namespace rtl::erase @@ -18,9 +20,14 @@ namespace rtl::erase template struct erased_method { - constexpr void hop(std::optional& p_return, const record_t& p_target, signature_ts&&...params) const noexcept + constexpr void hop_v(const record_t& p_target, signature_ts&&...params) const noexcept { - (*hopper)(this, p_return, p_target, std::forward(params)...); + (*hopper_v)(this, p_target, std::forward(params)...); + } + + ForceInline std::any hop_r(const record_t& p_target, signature_ts&&...params) const noexcept + { + return (*hopper_r)(this, p_target, std::forward(params)...); } GETTER(detail::RObjectId, _robject_id, robj_id); @@ -29,9 +36,13 @@ namespace rtl::erase using this_t = erased_method; - using functor_t = void(*)(const this_t*, std::optional& , const record_t&, signature_ts&&...); + using functor_vt = void(*)(const this_t*, const record_t& , signature_ts&&...); + + using functor_rt = std::any(*)(const this_t*, const record_t& , signature_ts&&...); + + functor_vt hopper_v = nullptr; - functor_t hopper = nullptr; + functor_rt hopper_r = nullptr; detail::RObjectId robj_id; }; diff --git a/ReflectionTemplateLib/rtl/inc/RObject.h b/ReflectionTemplateLib/rtl/inc/RObject.h index 26562732..b3b6a27a 100644 --- a/ReflectionTemplateLib/rtl/inc/RObject.h +++ b/ReflectionTemplateLib/rtl/inc/RObject.h @@ -43,7 +43,7 @@ namespace rtl const std::vector* m_converters = nullptr; RObject(const RObject&) = default; - RObject(std::any&& pObject, detail::RObjectId&& pRObjId, + RObject(std::any&& pObject, const detail::RObjectId& pRObjId, const std::vector* pConverters) noexcept; std::size_t getConverterIndex(const std::size_t pToTypeId) const; diff --git a/ReflectionTemplateLib/rtl/inc/RObject.hpp b/ReflectionTemplateLib/rtl/inc/RObject.hpp index 85a86213..b84b4bac 100644 --- a/ReflectionTemplateLib/rtl/inc/RObject.hpp +++ b/ReflectionTemplateLib/rtl/inc/RObject.hpp @@ -25,7 +25,7 @@ namespace rtl { - ForceInline RObject::RObject(std::any&& pObject, detail::RObjectId&& pRObjId, + ForceInline RObject::RObject(std::any&& pObject, const detail::RObjectId& pRObjId, const std::vector* pConverters) noexcept : m_object(std::in_place, std::move(pObject)) , m_objectId(pRObjId) From 22535c1375ccaa3a126f205bbc2f28264e20caf3 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Fri, 3 Oct 2025 00:13:21 +0530 Subject: [PATCH 53/58] erased-target method call benchmark added. --- .../src/ReflectedCallUnknownReturn.cpp | 78 ++++++++++++++----- .../src/ReflectedCallUnknownReturn.h | 12 ++- RTLBenchmarkApp/src/StandardCall.cpp | 4 +- RTLBenchmarkApp/src/StdFunction.cpp | 6 +- RTLBenchmarkApp/src/main.cpp | 10 ++- .../FunctionalityTests/ClassMethodsTests.cpp | 24 +++--- .../ConstMethodOverloadTests.cpp | 8 +- .../CopyConstructorTests.cpp | 16 ++-- .../FunctionalityTests/StaticMethodTests.cpp | 4 +- .../rtl/cache/cache_lambda_function.h | 6 +- .../rtl/cache/cache_lambda_method.h | 6 +- .../rtl/detail/inc/FunctionCaller.hpp | 9 ++- .../rtl/detail/inc/MethodInvoker.h | 5 +- .../rtl/detail/inc/MethodInvoker.hpp | 37 +++++++-- ReflectionTemplateLib/rtl/dispatch/lambda.h | 52 ++++--------- .../rtl/dispatch/lambda_function.h | 11 +-- .../rtl/dispatch/lambda_method.h | 17 ++-- .../rtl/dispatch/rtl_method_const.h | 2 +- .../rtl/erasure/CMakeLists.txt | 1 + .../rtl/erasure/aware_function.h | 13 ++-- .../rtl/erasure/aware_method.h | 46 ++++++++++- .../rtl/erasure/aware_method_const.h | 65 +++++++++++++--- .../rtl/erasure/erased_function.h | 27 +++++-- .../rtl/erasure/erased_method.h | 10 ++- ReflectionTemplateLib/rtl/erasure/erasure.h | 50 ++++++++++++ ReflectionTemplateLib/rtl/inc/Method.h | 23 +----- 26 files changed, 362 insertions(+), 180 deletions(-) create mode 100644 ReflectionTemplateLib/rtl/erasure/erasure.h diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index 294f8f60..d090cd8d 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -69,22 +69,22 @@ namespace return *method; }(); - // static const rtl::RObject nodeObj = []() - // { - // std::optional Node = cxx::mirror().getRecord("Node"); - // if (!Node) { - // std::cerr << "[x] error: record 'Node' not found.\n"; - // std::abort(); - // } - - // auto [err, robj] = Node->create(); - // if (robj.isEmpty()) { - // std::cout << "[x] error: " << rtl::to_string(err) << "\n"; - // } - // return std::move(robj); - // }(); + static const rtl::RObject nodeObj = []() + { + std::optional Node = cxx::mirror().getRecord("Node"); + if (!Node) { + std::cerr << "[x] error: record 'Node' not found.\n"; + std::abort(); + } + + auto [err, robj] = Node->create(); + if (robj.isEmpty()) { + std::cout << "[x] error: " << rtl::to_string(err) << "\n"; + } + return std::move(robj); + }(); } - + namespace { @@ -124,6 +124,26 @@ namespace return 0; }; + + static auto _test4 = []() + { + auto err = NodeSendMessage(nodeObj)(bm::g_longStr).err; + if (err != rtl::error::None) { + std::cout << "[01] error: " << rtl::to_string(err) << "\n"; + } + return 0; + }; + + + static auto _test5 = []() + { + auto err = NodeGetMessage(nodeObj)(bm::g_longStr).err; + if (err != rtl::error::None) { + std::cout << "[03] error: " << rtl::to_string(err) << "\n"; + } + return 0; + }; + static auto _new_line = []() { std::cout << std::endl; return 0; @@ -132,7 +152,7 @@ namespace -void RtlFunction_call_ReturnUnknown::typeVoid(benchmark::State& state) +void RtlFunction_call_ReturnUnknown::Void(benchmark::State& state) { static auto __= _new_line(); static auto _ = _test0(); @@ -143,7 +163,7 @@ void RtlFunction_call_ReturnUnknown::typeVoid(benchmark::State& state) } -void RtlFunction_call_ReturnUnknown::typeNonVoid(benchmark::State& state) +void RtlFunction_call_ReturnUnknown::NonVoid(benchmark::State& state) { static auto __= _new_line(); static auto _ = _test2(); @@ -154,7 +174,7 @@ void RtlFunction_call_ReturnUnknown::typeNonVoid(benchmark::State& state) } -void RtlFunction_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) +void RtlFunction_callMethod_ReturnUnknown::Void(benchmark::State& state) { static auto _ = _test1(); static bm::Node node; @@ -165,7 +185,7 @@ void RtlFunction_callMethod_ReturnUnknown::typeVoid(benchmark::State& state) } -void RtlFunction_callMethod_ReturnUnknown::typeNonVoid(benchmark::State& state) +void RtlFunction_callMethod_ReturnUnknown::NonVoid(benchmark::State& state) { static auto _ = _test3(); static bm::Node node; @@ -173,4 +193,24 @@ void RtlFunction_callMethod_ReturnUnknown::typeNonVoid(benchmark::State& state) { benchmark::DoNotOptimize(NodeGetMessage(node)(bm::g_longStr)); } +} + + +void RtlFunction_callMethod_ReturnUnknown::erasedTarget_Void(benchmark::State& state) +{ + static auto _ = _test4(); + for (auto _ : state) + { + benchmark::DoNotOptimize(NodeSendMessage(nodeObj)(bm::g_longStr)); + } +} + + +void RtlFunction_callMethod_ReturnUnknown::erasedTarget_NonVoid(benchmark::State& state) +{ + static auto _ = _test5(); + for (auto _ : state) + { + benchmark::DoNotOptimize(NodeGetMessage(nodeObj)(bm::g_longStr)); + } } \ No newline at end of file diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h index cc986820..37e0e049 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.h @@ -4,15 +4,19 @@ struct RtlFunction_call_ReturnUnknown { - static void typeVoid(benchmark::State& state); + static void Void(benchmark::State& state); - static void typeNonVoid(benchmark::State& state); + static void NonVoid(benchmark::State& state); }; struct RtlFunction_callMethod_ReturnUnknown { - static void typeVoid(benchmark::State& state); + static void Void(benchmark::State& state); - static void typeNonVoid(benchmark::State& state); + static void NonVoid(benchmark::State& state); + + static void erasedTarget_Void(benchmark::State& state); + + static void erasedTarget_NonVoid(benchmark::State& state); }; \ No newline at end of file diff --git a/RTLBenchmarkApp/src/StandardCall.cpp b/RTLBenchmarkApp/src/StandardCall.cpp index 30de3b2c..0f177969 100644 --- a/RTLBenchmarkApp/src/StandardCall.cpp +++ b/RTLBenchmarkApp/src/StandardCall.cpp @@ -10,8 +10,8 @@ namespace { static auto _put_line = []() { - std::cout << "------------------------------------------" - "--------------------------------------------------" << std::endl; + std::cout << "----------------------------------------------" + "-------------------------------------------------------" << std::endl; return 0; }; diff --git a/RTLBenchmarkApp/src/StdFunction.cpp b/RTLBenchmarkApp/src/StdFunction.cpp index c8d5647c..23b10b65 100644 --- a/RTLBenchmarkApp/src/StdFunction.cpp +++ b/RTLBenchmarkApp/src/StdFunction.cpp @@ -36,10 +36,8 @@ namespace bm std::function GetMessage = [](bm::argStr_t& pMsg) { - //Testing. - return std::any(bm::getMessage(pMsg)); - // auto retMsg = bm::getMessage(pMsg); - // return retMsg; + auto retMsg = bm::getMessage(pMsg); + return retMsg; }; std::function NodeGetMessage = [](bm::Node pNode, bm::argStr_t& pMsg) diff --git a/RTLBenchmarkApp/src/main.cpp b/RTLBenchmarkApp/src/main.cpp index 1c2c145d..f0dbc2bb 100644 --- a/RTLBenchmarkApp/src/main.cpp +++ b/RTLBenchmarkApp/src/main.cpp @@ -17,8 +17,9 @@ BENCHMARK(StdFunction_callMethod::returnVoid); BENCHMARK(RtlFunction_call::returnVoid); BENCHMARK(RtlFunction_callMethod::returnVoid); -BENCHMARK(RtlFunction_call_ReturnUnknown::typeVoid); -BENCHMARK(RtlFunction_callMethod_ReturnUnknown::typeVoid); +BENCHMARK(RtlFunction_call_ReturnUnknown::Void); +BENCHMARK(RtlFunction_callMethod_ReturnUnknown::Void); +BENCHMARK(RtlFunction_callMethod_ReturnUnknown::erasedTarget_Void); BENCHMARK(NativeCall::returnNonVoid); @@ -31,8 +32,9 @@ BENCHMARK(StdFunction_callMethod::returnNonVoid); BENCHMARK(RtlFunction_call::returnNonVoid); BENCHMARK(RtlFunction_callMethod::returnNonVoid); -BENCHMARK(RtlFunction_call_ReturnUnknown::typeNonVoid); -BENCHMARK(RtlFunction_callMethod_ReturnUnknown::typeNonVoid); +BENCHMARK(RtlFunction_call_ReturnUnknown::NonVoid); +BENCHMARK(RtlFunction_callMethod_ReturnUnknown::NonVoid); +BENCHMARK(RtlFunction_callMethod_ReturnUnknown::erasedTarget_NonVoid); namespace bm { diff --git a/RTLTestRunApp/src/FunctionalityTests/ClassMethodsTests.cpp b/RTLTestRunApp/src/FunctionalityTests/ClassMethodsTests.cpp index ffd62a06..bd10a2a5 100644 --- a/RTLTestRunApp/src/FunctionalityTests/ClassMethodsTests.cpp +++ b/RTLTestRunApp/src/FunctionalityTests/ClassMethodsTests.cpp @@ -82,7 +82,7 @@ namespace rtl_tests ASSERT_FALSE(book.isEmpty()); EXPECT_FALSE(setAuthor->hasSignature()); - auto [err1, ret] = (*setAuthor)(book)(book::AUTHOR); + auto [err1, ret] = setAuthor->bind(book).call(book::AUTHOR); EXPECT_TRUE(err1 == error::SignatureMismatch); ASSERT_TRUE(ret.isEmpty()); @@ -108,7 +108,7 @@ namespace rtl_tests ASSERT_FALSE(book.isEmpty()); EXPECT_FALSE(setAuthor->hasSignature()); - auto [err1, ret] = (*setAuthor)(book)(book::AUTHOR); + auto [err1, ret] = setAuthor->bind(book).call(book::AUTHOR); EXPECT_TRUE(err1 == error::SignatureMismatch); ASSERT_TRUE(ret.isEmpty()); @@ -134,7 +134,7 @@ namespace rtl_tests ASSERT_FALSE(book.isEmpty()); EXPECT_TRUE(getPublishedOn->hasSignature<>()); //empty template params checks for zero arguments. // Slower. bind<>().call() syntax is faster. - auto [err1, ret] = (*getPublishedOn)(book)(); + auto [err1, ret] = getPublishedOn->bind(book).call(); EXPECT_TRUE(err1 == error::None); ASSERT_FALSE(ret.isEmpty()); @@ -163,7 +163,7 @@ namespace rtl_tests ASSERT_FALSE(book.isEmpty()); EXPECT_TRUE(getPublishedOn->hasSignature<>()); //empty template params checks for zero arguments. - auto [err1, ret] = (*getPublishedOn)(book)(); + auto [err1, ret] = getPublishedOn->bind(book).call(); EXPECT_TRUE(err1 == error::None); ASSERT_FALSE(ret.isEmpty()); @@ -246,7 +246,7 @@ namespace rtl_tests ASSERT_FALSE(book.isEmpty()); EXPECT_TRUE(updateBookInfo->hasSignature<>()); //empty template params checks for zero arguments. - auto [err1, ret] = (*updateBookInfo)(book)(); + auto [err1, ret] = updateBookInfo->bind(book).call(); EXPECT_TRUE(err1 == error::None); ASSERT_TRUE(ret.isEmpty()); @@ -272,7 +272,7 @@ namespace rtl_tests ASSERT_FALSE(book.isEmpty()); EXPECT_TRUE(updateBookInfo->hasSignature<>()); //empty template params checks for zero arguments. - auto [err1, ret] = (*updateBookInfo)(book)(); + auto [err1, ret] = updateBookInfo->bind(book).call(); EXPECT_TRUE(err1 == error::None); ASSERT_TRUE(ret.isEmpty()); @@ -304,7 +304,7 @@ namespace rtl_tests std::string author = book::AUTHOR; const char* title = book::TITLE; - auto [err1, ret] = (*updateBookInfo)(book)(author, price, title); + auto [err1, ret] = updateBookInfo->bind(book).call(author, price, title); EXPECT_TRUE(err1 == error::None); ASSERT_TRUE(ret.isEmpty()); @@ -338,7 +338,7 @@ namespace rtl_tests std::string author = book::AUTHOR; const char* title = book::TITLE; - auto [err1, ret] = (*updateBookInfo)(book)(author, price, title); + auto [err1, ret] = updateBookInfo->bind(book).call(author, price, title); EXPECT_TRUE(err1 == error::None); ASSERT_TRUE(ret.isEmpty()); @@ -372,7 +372,7 @@ namespace rtl_tests std::string author = book::AUTHOR; const char* title = book::TITLE; - auto [err1, ret] = (*updateBookInfo)(book)(title, price, author); + auto [err1, ret] = updateBookInfo->bind(book).call(title, price, author); EXPECT_TRUE(err1 == error::None); ASSERT_TRUE(ret.isEmpty()); @@ -406,7 +406,7 @@ namespace rtl_tests std::string author = book::AUTHOR; const char* title = book::TITLE; - auto [err1, ret] = (*updateBookInfo)(book)(title, price, author); + auto [err1, ret] = updateBookInfo->bind(book).call(title, price, author); EXPECT_TRUE(err1 == error::None); ASSERT_TRUE(ret.isEmpty()); @@ -438,7 +438,7 @@ namespace rtl_tests //actual signature is 'const string', but we are passing 'string' as argument. which resolves to right call. //as long as any param_type in signature is not reference, const-qualifier do not matter. - auto [err1, ret] = (*addCopyrightTag)(book)(std::string(book::COPYRIGHT_TAG)); + auto [err1, ret] = addCopyrightTag->bind(book).call(std::string(book::COPYRIGHT_TAG)); EXPECT_TRUE(err1 == error::None); ASSERT_TRUE(ret.isEmpty()); @@ -470,7 +470,7 @@ namespace rtl_tests //actual signature is 'const string', but we are passing 'string' as argument. which resolves to right call. //as long as any param_type in signature is not reference, const-qualifier do not matter. - auto [err1, ret] = (*addCopyrightTag)(book)(std::string(book::COPYRIGHT_TAG)); + auto [err1, ret] = addCopyrightTag->bind(book).call(std::string(book::COPYRIGHT_TAG)); EXPECT_TRUE(err1 == error::None); ASSERT_TRUE(ret.isEmpty()); diff --git a/RTLTestRunApp/src/FunctionalityTests/ConstMethodOverloadTests.cpp b/RTLTestRunApp/src/FunctionalityTests/ConstMethodOverloadTests.cpp index 87ba39ce..874c66d0 100644 --- a/RTLTestRunApp/src/FunctionalityTests/ConstMethodOverloadTests.cpp +++ b/RTLTestRunApp/src/FunctionalityTests/ConstMethodOverloadTests.cpp @@ -177,13 +177,13 @@ namespace rtl_tests EXPECT_TRUE(updateLastName->hasSignature()); { string_view lastName = "invalid_arg"; - auto [err, ret] = (*updateLastName)(person)(lastName); + auto [err, ret] = updateLastName->bind(person).call(lastName); EXPECT_TRUE(err == error::SignatureMismatch); ASSERT_TRUE(ret.isEmpty()); } { string lastName = person::LAST_NAME; - auto [err, ret] = (*updateLastName)(person)(lastName); + auto [err, ret] = updateLastName->bind(person).call(lastName); EXPECT_TRUE(err == error::None); ASSERT_TRUE(ret.isEmpty()); @@ -214,13 +214,13 @@ namespace rtl_tests EXPECT_TRUE(updateLastName->hasSignature()); { string_view lastName = "invalid_arg"; - auto [err, ret] = (*updateLastName)(person)(lastName); + auto [err, ret] = updateLastName->bind(person).call(lastName); EXPECT_TRUE(err == error::SignatureMismatch); ASSERT_TRUE(ret.isEmpty()); } { string lastName = person::LAST_NAME; - auto [err, ret] = (*updateLastName)(person)(lastName); + auto [err, ret] = updateLastName->bind(person).call(lastName); EXPECT_TRUE(err == error::None); ASSERT_TRUE(ret.isEmpty()); diff --git a/RTLTestRunApp/src/FunctionalityTests/CopyConstructorTests.cpp b/RTLTestRunApp/src/FunctionalityTests/CopyConstructorTests.cpp index a0de7709..86ba0331 100644 --- a/RTLTestRunApp/src/FunctionalityTests/CopyConstructorTests.cpp +++ b/RTLTestRunApp/src/FunctionalityTests/CopyConstructorTests.cpp @@ -126,10 +126,10 @@ namespace rtl_tests EXPECT_TRUE(err0 == error::None); ASSERT_FALSE(book.isEmpty()); - auto [err1, ret1] = (*setAuthor)(book)(author); + auto [err1, ret1] = setAuthor->bind(book).call(author); EXPECT_TRUE(err1 == error::None); - auto [err2, ret2] = (*setDecription)(book)(description); + auto [err2, ret2] = setDecription->bind(book).call(description); EXPECT_TRUE(err1 == error::None); auto [err3, bookCopy] = book.clone(); @@ -168,10 +168,10 @@ namespace rtl_tests EXPECT_TRUE(err0 == error::None); ASSERT_FALSE(book.isEmpty()); - auto [err1, ret1] = (*setAuthor)(book)(author); + auto [err1, ret1] = setAuthor->bind(book).call(author); EXPECT_TRUE(err1 == error::None); - auto [err2, ret2] = (*setDecription)(book)(description); + auto [err2, ret2] = setDecription->bind(book).call(description); EXPECT_TRUE(err1 == error::None); auto [err3, bookCopy] = book.clone(); @@ -210,10 +210,10 @@ namespace rtl_tests EXPECT_TRUE(err0 == error::None); ASSERT_FALSE(book.isEmpty()); - auto [err1, ret1] = (*setAuthor)(book)(author); + auto [err1, ret1] = setAuthor->bind(book).call(author); EXPECT_TRUE(err1 == error::None); - auto [err2, ret2] = (*setDecription)(book)(description); + auto [err2, ret2] = setDecription->bind(book).call(description); EXPECT_TRUE(err1 == error::None); auto [err3, bookCopy] = book.clone(); @@ -252,10 +252,10 @@ namespace rtl_tests EXPECT_TRUE(err0 == error::None); ASSERT_FALSE(book.isEmpty()); - auto [err1, ret1] = (*setAuthor)(book)(author); + auto [err1, ret1] = setAuthor->bind(book).call(author); EXPECT_TRUE(err1 == error::None); - auto [err2, ret2] = (*setDecription)(book)(description); + auto [err2, ret2] = setDecription->bind(book).call(description); EXPECT_TRUE(err1 == error::None); auto [err3, bookCopy] = book.clone(); diff --git a/RTLTestRunApp/src/FunctionalityTests/StaticMethodTests.cpp b/RTLTestRunApp/src/FunctionalityTests/StaticMethodTests.cpp index f8a80759..db6de258 100644 --- a/RTLTestRunApp/src/FunctionalityTests/StaticMethodTests.cpp +++ b/RTLTestRunApp/src/FunctionalityTests/StaticMethodTests.cpp @@ -121,7 +121,7 @@ namespace rtl_tests EXPECT_TRUE(err0 == error::None); ASSERT_FALSE(person.isEmpty()); { - auto [err, ret] = (*getDefaults)(person)(); + auto [err, ret] = getDefaults->bind(person).call(); EXPECT_TRUE(err == error::None); ASSERT_FALSE(ret.isEmpty()); EXPECT_TRUE(ret.canViewAs()); @@ -168,7 +168,7 @@ namespace rtl_tests EXPECT_EQ(retStr, checkStr); } { - auto [err, ret] = (*getProfile)(person)(occupation, age); + auto [err, ret] = getProfile->bind(person).call(occupation, age); EXPECT_TRUE(err == error::None); ASSERT_FALSE(ret.isEmpty()); diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h index e7eccd61..35023d85 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_function.h @@ -29,12 +29,10 @@ namespace rtl::cache const dispatch::lambda_function& push(const dispatch::functor& p_functor) const { - m_erasure_cache.push_back(erase::aware_function()); - erase::erased_function* erasure = &m_erasure_cache.back(); + m_erasure_cache.push_back(erase::aware_function(p_functor)); + m_cache.push_back(dispatch::lambda_function(p_functor, m_erasure_cache.back())); - m_cache.push_back(dispatch::lambda_function(p_functor, erasure)); p_functor.m_lambda = &m_cache.back(); - m_erasure_cache.back().m_function = m_cache.back().template get_hopper(); return m_cache.back(); diff --git a/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h b/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h index f2582276..f4200da9 100644 --- a/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h +++ b/ReflectionTemplateLib/rtl/cache/cache_lambda_method.h @@ -30,12 +30,10 @@ namespace rtl::cache const dispatch::lambda_method& push(const dispatch::functor& p_functor) const { - m_erasure_cache.push_back(erase::aware_method()); - erase::erased_method* erasure = &m_erasure_cache.back(); + m_erasure_cache.push_back(erase::aware_method(p_functor)); + m_cache.push_back(dispatch::lambda_method(p_functor, m_erasure_cache.back())); - m_cache.push_back(dispatch::lambda_method(p_functor, erasure)); p_functor.m_lambda = &m_cache.back(); - m_erasure_cache.back().m_method = m_cache.back().template get_hopper(); return m_cache.back(); diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index c662b825..2b8a2001 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -43,17 +43,18 @@ namespace rtl::detail auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { - auto caller = functorId->template get_lambda_function<_args...>()->m_erasure; + const auto& erased = functorId->m_lambda->m_erasure; + const auto& caller = erased.to_erased_ret_function<_args...>(); if(functorId->m_lambda->is_void()) { - caller->hop_v(std::forward<_args>(params)...); + caller.hop_v(std::forward<_args>(params)...); return { error::None, RObject{} }; } else { return{ error::None, - RObject{ caller->hop_r(std::forward<_args>(params)...), - caller->get_robject_id(), nullptr } + RObject{ caller.hop_r(std::forward<_args>(params)...), + caller.get_return_robj_id(), nullptr } }; } } diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h index 7654618e..55f9d9f9 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h @@ -23,7 +23,10 @@ namespace rtl::detail const _recordType& m_target; - template + template requires (std::is_same_v, RObject> == false) + constexpr Return operator()(_args&&...params) const noexcept; + + template requires (std::is_same_v, RObject> == true) constexpr Return operator()(_args&&...params) const noexcept; }; } diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index 0135bf47..cfa01062 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -187,26 +187,53 @@ namespace rtl::detail namespace rtl::detail { template - template + template requires (std::is_same_v, RObject> == false) ForceInline constexpr Return ErasedInvoker<_recordType>::operator()(_args&&...params) const noexcept { auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { - auto caller = functorId->template get_lambda_method<_recordType, _args...>()->m_erasure; + const auto& erased = functorId->m_lambda->m_erasure; + const auto& caller = erased.to_erased_ret_method<_recordType, _args...>(); if(functorId->m_lambda->is_void()) { - caller->hop_v(m_target, std::forward<_args>(params)...); + caller.hop_v(m_target, std::forward<_args>(params)...); return { error::None, RObject{} }; } else { return{ error::None, - RObject{ caller->hop_r(m_target, std::forward<_args>(params)...), - caller->get_robject_id(), nullptr } + RObject{ caller.hop_r(m_target, std::forward<_args>(params)...), + caller.get_return_robj_id(), nullptr } }; } } else return { error::SignatureMismatch, RObject{} }; } + + + template + template requires (std::is_same_v, RObject> == true) + ForceInline constexpr Return ErasedInvoker<_recordType>::operator()(_args&&...params) const noexcept + { + auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); + if (functorId) [[likely]] + { + const auto& erased = functorId->m_lambda->m_erasure; + const auto& caller = erased.to_erased_ret_function<_args...>(); + if (functorId->m_lambda->is_void()) + { + caller.hop_v(m_target, std::forward<_args>(params)...); + return { error::None, RObject{} }; + } + else + { + return{ error::None, + RObject{ caller.hop_r(m_target, std::forward<_args>(params)...), + caller.get_return_robj_id(), nullptr } + }; + } + } + else return { error::SignatureMismatch, RObject{} }; + } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda.h b/ReflectionTemplateLib/rtl/dispatch/lambda.h index 15ec6e99..052f5772 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda.h @@ -13,27 +13,19 @@ #include "rtl_traits.h" #include "functor.h" +#include "erasure.h" namespace rtl::dispatch { struct lambda_base { - const functor& m_functor; - - const bool m_is_void; - -// protected: - - lambda_base(const functor& p_functor) noexcept - : m_functor(p_functor) - , m_is_void(p_functor.m_returnId == detail::TypeId::get()) - { } + constexpr bool is_void() const + { + return m_is_void; + } template using function_t = lambda_function; - - template - using method_t = lambda_method; template constexpr const function_t* to_function(std::size_t p_argsId) const @@ -45,6 +37,9 @@ namespace rtl::dispatch else return nullptr; } + template + using method_t = lambda_method; + template constexpr const method_t* to_method(std::size_t p_recordId, std::size_t p_argsId) const { @@ -56,33 +51,18 @@ namespace rtl::dispatch else return nullptr; } -// public: - GETTER_CREF(functor, _functor, m_functor); - constexpr bool is_void() const { - return m_is_void; - } - - template - constexpr bool is_returning() const - { - return (m_functor.m_returnId == detail::TypeId::get()); - } + lambda_base(const functor& p_functor, const erase::erasure_base& p_erasure) noexcept + : m_is_void(p_functor.m_returnId == detail::TypeId::get()) + , m_functor(p_functor) + , m_erasure(p_erasure) + { } - template - constexpr bool is_signature() const - { - return (m_functor.m_signatureId == detail::TypeId...>>::get()); - } + const bool m_is_void; - template - constexpr bool is_member() const - { - return (m_functor.m_recordId == detail::TypeId::get() || - m_functor.m_recordId == detail::TypeId::get()); - } + const functor& m_functor; - friend detail::FunctorId; + const erase::erasure_base& m_erasure; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h index 2e62c42d..e1f4e097 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_function.h @@ -24,13 +24,6 @@ namespace rtl::dispatch template using hopper_t = rtl::function; - erase::erased_function* m_erasure; - - lambda_function(const functor& p_functor, erase::erased_function* p_erasure) noexcept - : lambda_base(p_functor) - , m_erasure(p_erasure) - { } - template constexpr const hopper_t get_hopper(const std::size_t p_returnId = 0) const { @@ -41,5 +34,9 @@ namespace rtl::dispatch } return hopper_t(); } + + lambda_function(const functor& p_functor, const erase::erased_function& p_erasure) noexcept + : lambda_base(p_functor, p_erasure) + { } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h index 6e5c1cc6..3b673655 100644 --- a/ReflectionTemplateLib/rtl/dispatch/lambda_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/lambda_method.h @@ -26,16 +26,6 @@ namespace rtl::dispatch template using hopper_t = rtl::method; - template - using hopper_ct = rtl::method; - - erase::erased_method* m_erasure; - - lambda_method(const functor& p_functor, erase::erased_method* p_erasure) noexcept - : lambda_base(p_functor) - , m_erasure(p_erasure) - { } - template requires (std::is_const_v == false) constexpr const hopper_t get_hopper(std::size_t p_returnId = 0) const { @@ -47,6 +37,9 @@ namespace rtl::dispatch return hopper_t(); } + template + using hopper_ct = rtl::method; + template requires (std::is_const_v == true) constexpr const hopper_ct get_hopper(std::size_t p_returnId = 0) const { @@ -57,5 +50,9 @@ namespace rtl::dispatch } return hopper_ct(); } + + lambda_method(const functor& p_functor, const erase::erased_method& p_erasure) noexcept + : lambda_base(p_functor, p_erasure) + { } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h b/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h index 5b4edf73..b7e46b22 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h @@ -31,7 +31,7 @@ namespace rtl } template - [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept//(noexcept_v) + [[nodiscard]] constexpr decltype(auto) operator()(const record_t& target, args_t&&...params) const noexcept//(noexcept_v) { //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (target.*m_functor)(std::forward(params)...); diff --git a/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt b/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt index b2f4a6d3..c25d8afc 100644 --- a/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt +++ b/ReflectionTemplateLib/rtl/erasure/CMakeLists.txt @@ -3,6 +3,7 @@ # Collect headers in this folder (absolute paths) set(LOCAL_HEADERS + "${CMAKE_CURRENT_SOURCE_DIR}/erasure.h" "${CMAKE_CURRENT_SOURCE_DIR}/erased_method.h" "${CMAKE_CURRENT_SOURCE_DIR}/erased_function.h" diff --git a/ReflectionTemplateLib/rtl/erasure/aware_function.h b/ReflectionTemplateLib/rtl/erasure/aware_function.h index 80a3282d..4c4d3115 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_function.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_function.h @@ -13,7 +13,6 @@ #include #include "erased_function.h" -#include "rtl_constants.h" namespace rtl::erase { @@ -26,13 +25,13 @@ namespace rtl::erase using this_t = aware_function; - aware_function() - { - constexpr bool isConstCastSafe = (!traits::is_const_v); + constexpr static bool isConstCastSafe = (!traits::is_const_v); + aware_function(const dispatch::functor& p_functor) + : base_t(p_functor, detail::RObjectId::create(isConstCastSafe)) + { base_t::hopper_v = hop_v; base_t::hopper_r = hop_r; - base_t::robj_id = detail::RObjectId::create(isConstCastSafe); } constexpr static void hop_v(const base_t* p_this, signature_ts&&...params) noexcept @@ -62,8 +61,8 @@ namespace rtl::erase } else { - using rconst_t = std::add_const_t>; - return std::any(rconst_t(std::forward(ret_v))); + using raw_ct = std::add_const_t>; + return std::any(raw_ct(std::forward(ret_v))); } } else return std::any(); diff --git a/ReflectionTemplateLib/rtl/erasure/aware_method.h b/ReflectionTemplateLib/rtl/erasure/aware_method.h index 6eee7ce6..0a7f7066 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_method.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_method.h @@ -26,13 +26,15 @@ namespace rtl::erase rtl::method m_method; - aware_method() - { - constexpr bool isConstCastSafe = (!traits::is_const_v); + constexpr static bool isConstCastSafe = (!traits::is_const_v); + aware_method(const dispatch::functor& p_functor) + : base_t(p_functor, detail::RObjectId::create(isConstCastSafe)) + { base_t::hopper_v = hop_v; base_t::hopper_r = hop_r; - base_t::robj_id = detail::RObjectId::create(isConstCastSafe); + base_t::base_t::hopper_robj_v = hop_robj_v; + base_t::base_t::hopper_robj_r = hop_robj_r; } constexpr static void hop_v(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept @@ -44,6 +46,16 @@ namespace rtl::erase } } + constexpr static void hop_robj_v(const base_t::base_t* p_this, const rtl::RObject& p_target, signature_ts&&...params) noexcept + { + if constexpr (std::is_void_v) + { + const auto& target = p_target.view()->get(); + auto this_p = static_cast(p_this); + this_p->m_method(const_cast(target), std::forward(params)...); + } + } + ForceInline static std::any hop_r(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept { if constexpr (!std::is_void_v) @@ -68,5 +80,31 @@ namespace rtl::erase } else return std::any(); } + + ForceInline static std::any hop_robj_r(const base_t::base_t* p_this, const rtl::RObject& p_target, signature_ts&&...params) noexcept + { + if constexpr (!std::is_void_v) + { + const auto& target = p_target.view()->get(); + auto this_p = static_cast(p_this); + auto&& ret_v = this_p->m_method(const_cast(target), std::forward(params)...); + if constexpr (std::is_pointer_v) + { + using raw_t = std::remove_pointer_t; + return std::any(static_cast(ret_v)); + } + else if constexpr (std::is_reference_v) + { + using raw_t = std::remove_cv_t>; + return std::any(static_cast(&ret_v)); + } + else + { + using rconst_t = std::add_const_t>; + return std::any(rconst_t(std::forward(ret_v))); + } + } + else return std::any(); + } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/aware_method_const.h b/ReflectionTemplateLib/rtl/erasure/aware_method_const.h index 6c02f0af..971fdea7 100644 --- a/ReflectionTemplateLib/rtl/erasure/aware_method_const.h +++ b/ReflectionTemplateLib/rtl/erasure/aware_method_const.h @@ -29,36 +29,81 @@ namespace rtl::erase { constexpr bool isConstCastSafe = (!traits::is_const_v); - base_t::hopper = hopper; - base_t::robj_id = detail::RObjectId::create(isConstCastSafe); + base_t::hopper_v = hop_v; + base_t::hopper_r = hop_r; + base_t::base_t::hopper_robj_v = hop_robj_v; + base_t::base_t::hopper_robj_r = hop_robj_r; + base_t::base_t::return_obj_id = detail::RObjectId::create(isConstCastSafe); } - constexpr static void hopper(const base_t* p_this, std::optional& p_return, const record_t& p_target, signature_ts&&...params) noexcept + constexpr static void hop_v(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept { - auto this_p = static_cast(p_this); - - if constexpr (std::is_void_v) { + if constexpr (std::is_void_v) + { + auto this_p = static_cast(p_this); this_p->m_method(p_target, std::forward(params)...); } - else { + } + + constexpr static void hop_robj_v(const base_t::base_t* p_this, const rtl::RObject& p_target, signature_ts&&...params) noexcept + { + if constexpr (std::is_void_v) + { + const auto& target = p_target.view()->get(); + auto this_p = static_cast(p_this); + this_p->m_method(target, std::forward(params)...); + } + } + + ForceInline static std::any hop_r(const base_t* p_this, const record_t& p_target, signature_ts&&...params) noexcept + { + if constexpr (!std::is_void_v) + { + auto this_p = static_cast(p_this); auto&& ret_v = this_p->m_method(p_target, std::forward(params)...); + if constexpr (std::is_pointer_v) + { + using raw_t = std::remove_pointer_t; + return std::any(static_cast(ret_v)); + } + else if constexpr (std::is_reference_v) + { + using raw_t = std::remove_cv_t>; + return std::any(static_cast(&ret_v)); + } + else + { + using rconst_t = std::add_const_t>; + return std::any(rconst_t(std::forward(ret_v))); + } + } + else return std::any(); + } + ForceInline static std::any hop_robj_r(const base_t::base_t* p_this, const rtl::RObject& p_target, signature_ts&&...params) noexcept + { + if constexpr (!std::is_void_v) + { + const auto& target = p_target.view()->get(); + auto this_p = static_cast(p_this); + auto&& ret_v = this_p->m_method(target, std::forward(params)...); if constexpr (std::is_pointer_v) { using raw_t = std::remove_pointer_t; - p_return.emplace(static_cast(ret_v)); + return std::any(static_cast(ret_v)); } else if constexpr (std::is_reference_v) { using raw_t = std::remove_cv_t>; - p_return.emplace(static_cast(&ret_v)); + return std::any(static_cast(&ret_v)); } else { using rconst_t = std::add_const_t>; - p_return.emplace(rconst_t(std::forward(ret_v))); + return std::any(rconst_t(std::forward(ret_v))); } } + else return std::any(); } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erased_function.h b/ReflectionTemplateLib/rtl/erasure/erased_function.h index 08a76e03..749451eb 100644 --- a/ReflectionTemplateLib/rtl/erasure/erased_function.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_function.h @@ -12,13 +12,12 @@ #pragma once #include "RObjectId.h" -#include "rtl_forward_decls.h" -#include "rtl_typeid.h" +#include "erasure.h" namespace rtl::erase { template - struct erased_function + struct erased_function : erasure_base { constexpr void hop_v(signature_ts&&...params) const noexcept { @@ -30,7 +29,15 @@ namespace rtl::erase return (*hopper_r)(this, std::forward(params)...); } - GETTER(detail::RObjectId, _robject_id, robj_id); + constexpr void hop_v(const RObject& p_robj, signature_ts&&...params) const noexcept + { + (*hopper_robj_v)(this, p_robj, std::forward(params)...); + } + + ForceInline std::any hop_r(const RObject& p_robj, signature_ts&&...params) const noexcept + { + return (*hopper_robj_r)(this, p_robj, std::forward(params)...); + } protected: @@ -40,10 +47,20 @@ namespace rtl::erase using functor_rt = std::any(*)(const this_t*, signature_ts&&...); + using func_ro_vt = void(*)(const this_t*, const RObject&, signature_ts&&...); + + using func_ro_rt = std::any(*)(const this_t*, const RObject&, signature_ts&&...); + functor_vt hopper_v = nullptr; functor_rt hopper_r = nullptr; - detail::RObjectId robj_id; + func_ro_vt hopper_robj_v = nullptr; + + func_ro_rt hopper_robj_r = nullptr; + + erased_function(const dispatch::functor& p_functor, const detail::RObjectId& p_robj_id) noexcept + : erasure_base(p_functor, p_robj_id) + { } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erased_method.h b/ReflectionTemplateLib/rtl/erasure/erased_method.h index 2a725312..75101af2 100644 --- a/ReflectionTemplateLib/rtl/erasure/erased_method.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_method.h @@ -18,7 +18,7 @@ namespace rtl::erase { template - struct erased_method + struct erased_method : erased_function { constexpr void hop_v(const record_t& p_target, signature_ts&&...params) const noexcept { @@ -30,10 +30,10 @@ namespace rtl::erase return (*hopper_r)(this, p_target, std::forward(params)...); } - GETTER(detail::RObjectId, _robject_id, robj_id); - protected: + using base_t = erased_function; + using this_t = erased_method; using functor_vt = void(*)(const this_t*, const record_t& , signature_ts&&...); @@ -44,6 +44,8 @@ namespace rtl::erase functor_rt hopper_r = nullptr; - detail::RObjectId robj_id; + erased_method(const dispatch::functor& p_functor, const detail::RObjectId& p_robj_id) noexcept + : base_t(p_functor, p_robj_id) + { } }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erasure.h b/ReflectionTemplateLib/rtl/erasure/erasure.h new file mode 100644 index 00000000..02001436 --- /dev/null +++ b/ReflectionTemplateLib/rtl/erasure/erasure.h @@ -0,0 +1,50 @@ +/************************************************************************* + * * + * Reflection Template Library (RTL) - Modern C++ Reflection Framework * + * https://github.com/ReflectCxx/ReflectionTemplateLibrary-CPP * + * * + * Copyright (c) 2025 Neeraj Singh * + * SPDX-License-Identifier: MIT * + * * + *************************************************************************/ + + +#pragma once + +#include "functor.h" +#include "RObjectId.h" + +namespace rtl::erase +{ + struct erasure_base + { + template + using function_t = erased_function; + + template + constexpr const function_t& to_erased_ret_function() const + { + return static_cast&>(*this); + } + + template + using method_t = erased_method; + + template + constexpr const method_t& to_erased_ret_method() const + { + return static_cast&>(*this); + } + + erasure_base(const dispatch::functor& p_functor, const detail::RObjectId& p_robj_id) noexcept + : m_functor(p_functor) + , m_ret_obj_id(p_robj_id) + { } + + const dispatch::functor& m_functor; + + const detail::RObjectId m_ret_obj_id; + + GETTER(detail::RObjectId, _return_robj_id, m_ret_obj_id); + }; +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index d298fb60..343cf22e 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -53,6 +53,9 @@ namespace rtl { using Function::bind; + template + constexpr const detail::FunctionCaller<_args...> operator()(_args&&...params) const noexcept = delete; + GETTER_BOOL(Const, (getQualifier() == detail::methodQ::Const)); template @@ -69,29 +72,11 @@ namespace rtl { const detail::NonConstInvoker<_signature...> bind(constCast&& pTarget) const; template - constexpr const detail::ErasedInvoker<_recordType> operator()(const _recordType& pTarget) const + constexpr const detail::ErasedInvoker<_recordType> operator()(_recordType&& pTarget) const { return detail::ErasedInvoker<_recordType>{ (*this), pTarget }; } - - /* @method: operator()(const RObject&) - @param: const RObject& (target object) - @return: lambda - * accepts 'pTarget', which contains the actual object on which the member-function functor associated with 'this' is invoked. - * returns a lambda, which forwards the call to 'call', finally invoking the associated non-static-member-function functor. - * provides syntax like, 'method(pTarget)(params...)', keeping the target & params seperate. - */ constexpr detail::DefaultInvoker<> operator()(const RObject& pTarget) const - { - return detail::DefaultInvoker<>{ this, &pTarget }; - } - - constexpr detail::NonConstInvoker<> operator()(constCast&& pTarget) const - { - return detail::NonConstInvoker<>{ this, &pTarget.m_target }; - } - - //friends :) friend Record; friend detail::CxxReflection; From 7cc85de39193bb99e6c3183f56c65bd8e0902bf3 Mon Sep 17 00:00:00 2001 From: neeraj Date: Fri, 3 Oct 2025 00:31:40 +0530 Subject: [PATCH 54/58] fix gcc/clang compile error. --- RTLBenchmarkApp/src/StandardCall.cpp | 2 +- RTLBenchmarkApp/src/StdFunction.cpp | 2 +- ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp | 2 +- ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp | 4 ++-- 4 files changed, 5 insertions(+), 5 deletions(-) diff --git a/RTLBenchmarkApp/src/StandardCall.cpp b/RTLBenchmarkApp/src/StandardCall.cpp index 0f177969..f27a11b0 100644 --- a/RTLBenchmarkApp/src/StandardCall.cpp +++ b/RTLBenchmarkApp/src/StandardCall.cpp @@ -34,7 +34,7 @@ namespace bm extern std::function NodeSendMessage; - extern std::function GetMessage; + extern std::function GetMessage; extern std::function NodeGetMessage; } diff --git a/RTLBenchmarkApp/src/StdFunction.cpp b/RTLBenchmarkApp/src/StdFunction.cpp index 23b10b65..b258b02d 100644 --- a/RTLBenchmarkApp/src/StdFunction.cpp +++ b/RTLBenchmarkApp/src/StdFunction.cpp @@ -34,7 +34,7 @@ namespace bm pNode.sendMessage(pMsg); }; - std::function GetMessage = [](bm::argStr_t& pMsg) + std::function GetMessage = [](bm::argStr_t& pMsg) { auto retMsg = bm::getMessage(pMsg); return retMsg; diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index 2b8a2001..aa9f6822 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -44,7 +44,7 @@ namespace rtl::detail if (functorId) [[likely]] { const auto& erased = functorId->m_lambda->m_erasure; - const auto& caller = erased.to_erased_ret_function<_args...>(); + const auto& caller = erased.template to_erased_ret_function<_args...>(); if(functorId->m_lambda->is_void()) { caller.hop_v(std::forward<_args>(params)...); diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index cfa01062..284aedc1 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -194,7 +194,7 @@ namespace rtl::detail if (functorId) [[likely]] { const auto& erased = functorId->m_lambda->m_erasure; - const auto& caller = erased.to_erased_ret_method<_recordType, _args...>(); + const auto& caller = erased.template to_erased_ret_method<_recordType, _args...>(); if(functorId->m_lambda->is_void()) { caller.hop_v(m_target, std::forward<_args>(params)...); @@ -220,7 +220,7 @@ namespace rtl::detail if (functorId) [[likely]] { const auto& erased = functorId->m_lambda->m_erasure; - const auto& caller = erased.to_erased_ret_function<_args...>(); + const auto& caller = erased.template to_erased_ret_function<_args...>(); if (functorId->m_lambda->is_void()) { caller.hop_v(m_target, std::forward<_args>(params)...); From 40c76613fc6cd6ea4ab8cbc0c77b8d049efb2e3e Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Sat, 4 Oct 2025 00:34:39 +0530 Subject: [PATCH 55/58] interface refactored, tests added for known-type-calls. --- .../src/ReflectedCallKnownReturn.cpp | 12 +- .../src/ReflectedCallUnknownReturn.cpp | 8 +- RTLTestRunApp/src/CMakeLists.txt | 1 + .../StaticTypeCFunctionTests.cpp | 189 ++++++++++++++++++ .../rtl/detail/inc/FunctionCaller.h | 2 +- .../rtl/detail/inc/FunctionCaller.hpp | 50 ++--- .../rtl/detail/inc/MethodInvoker.hpp | 12 +- .../rtl/dispatch/rtl_function.h | 5 +- .../rtl/dispatch/rtl_method.h | 5 +- .../rtl/dispatch/rtl_method_const.h | 5 +- .../rtl/erasure/erased_function.h | 8 +- .../rtl/erasure/erased_method.h | 4 +- ReflectionTemplateLib/rtl/erasure/erasure.h | 6 +- ReflectionTemplateLib/rtl/inc/Function.h | 15 +- ReflectionTemplateLib/rtl/inc/Function.hpp | 18 +- ReflectionTemplateLib/rtl/inc/Method.h | 4 +- ReflectionTemplateLib/rtl/inc/Method.hpp | 2 +- ReflectionTemplateLib/rtl/inc/RObject.h | 2 +- ReflectionTemplateLib/rtl/rtl_forward_decls.h | 2 +- 19 files changed, 263 insertions(+), 87 deletions(-) create mode 100644 RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index f03456ba..4d17b05c 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -28,7 +28,7 @@ namespace std::cerr << "[00] error: erase_function 'getMessage' not found."; std::abort(); } - return function->lambda().argsT().returnT(); + return function->to().argsT().returnT(); }(); static const rtl::function sendMessage = []() @@ -39,7 +39,7 @@ namespace std::cerr << "[01] error: erase_function 'sendMessage' not found."; std::abort(); } - return function->lambda().argsT().returnT(); + return function->to().argsT().returnT(); }(); static const rtl::method getMessageNode = []() @@ -55,7 +55,7 @@ namespace std::cerr << "[02] error: method 'Node::getMessage' not found."; std::abort(); } - return method->lambda().argsT().returnT(); + return method->to().argsT().returnT(); }(); static const rtl::method sendMessageNode = []() @@ -71,7 +71,7 @@ namespace std::cerr << "[3] error: method 'Node::sendMessage' not found."; std::abort(); } - return method->lambda().argsT().returnT(); + return method->to().argsT().returnT(); }(); } @@ -84,9 +84,9 @@ namespace }; template - static bool test(const T& lambda, int callerId) + static bool test(const T& to, int callerId) { - if (!lambda) { + if (!to) { std::cerr << "[" << callerId << "] error: functor not valid, return-type or signature mismatch."; std::abort(); } diff --git a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp index d090cd8d..cb3a19c0 100644 --- a/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallUnknownReturn.cpp @@ -90,7 +90,7 @@ namespace { static auto _test0 = []() { - auto err = SendMessage()(bm::g_longStr).err; + auto err = SendMessage(bm::g_longStr).err; if (err != rtl::error::None) { std::cout << "[00] error: " << rtl::to_string(err) << "\n"; } @@ -108,7 +108,7 @@ namespace static auto _test2 = []() { - auto err = GetMessage()(bm::g_longStr).err; + auto err = GetMessage(bm::g_longStr).err; if (err != rtl::error::None) { std::cout << "[02] error: " << rtl::to_string(err) << "\n"; } @@ -158,7 +158,7 @@ void RtlFunction_call_ReturnUnknown::Void(benchmark::State& state) static auto _ = _test0(); for (auto _ : state) { - benchmark::DoNotOptimize(SendMessage()(bm::g_longStr)); + benchmark::DoNotOptimize(SendMessage(bm::g_longStr)); } } @@ -169,7 +169,7 @@ void RtlFunction_call_ReturnUnknown::NonVoid(benchmark::State& state) static auto _ = _test2(); for (auto _ : state) { - benchmark::DoNotOptimize(GetMessage()(bm::g_longStr)); + benchmark::DoNotOptimize(GetMessage(bm::g_longStr)); } } diff --git a/RTLTestRunApp/src/CMakeLists.txt b/RTLTestRunApp/src/CMakeLists.txt index e5d3fc3f..5e0400f4 100644 --- a/RTLTestRunApp/src/CMakeLists.txt +++ b/RTLTestRunApp/src/CMakeLists.txt @@ -6,6 +6,7 @@ project(RTLTestRunApp) # Create a variable containing the source files for your target set(LOCAL_SOURCES_0 "${CMAKE_CURRENT_LIST_DIR}/FunctionalityTests/ClassMethodsTests.cpp" + "${CMAKE_CURRENT_LIST_DIR}/FunctionalityTests/StaticTypeCFunctionTests.cpp" "${CMAKE_CURRENT_LIST_DIR}/FunctionalityTests/ConstMethodOverloadTests.cpp" "${CMAKE_CURRENT_LIST_DIR}/FunctionalityTests/ConstructorTests.cpp" "${CMAKE_CURRENT_LIST_DIR}/FunctionalityTests/CopyConstructorTests.cpp" diff --git a/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp b/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp new file mode 100644 index 00000000..51c7d0cd --- /dev/null +++ b/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp @@ -0,0 +1,189 @@ + +#include +#include + +#include "TestMirrorProvider.h" +#include "GlobalTestUtils.h" + + +using namespace test_utils; +using namespace test_mirror; + +namespace rtl_tests +{ + TEST(StaticTypeQuery, get_namespace_function_types) + { + std::optional setReal = cxx::mirror().getFunction(str_complex, str_setReal); + ASSERT_TRUE(setReal); + { + EXPECT_TRUE(setReal->getNamespace() == str_complex); + EXPECT_TRUE(setReal->getFunctionName() == str_setReal); + { + rtl::function functor = setReal->to().argsT().returnT(); + ASSERT_TRUE(functor); + } { + rtl::function functor = setReal->to().argsT().returnT(); + ASSERT_FALSE(functor); + } + } + + std::optional setImaginary = cxx::mirror().getFunction(str_complex, str_setImaginary); + ASSERT_TRUE(setImaginary); + { + EXPECT_TRUE(setImaginary->getNamespace() == str_complex); + EXPECT_TRUE(setImaginary->getFunctionName() == str_setImaginary); + { + rtl::function functor = setImaginary->to().argsT().returnT(); + ASSERT_TRUE(functor); + } { + rtl::function functor = setImaginary->to().argsT().returnT(); + ASSERT_FALSE(functor); + } + } + } + + + TEST(StaticTypeQuery, namespace_function_execute_return) + { + std::optional getMagnitude = cxx::mirror().getFunction(str_complex, str_getMagnitude); + ASSERT_TRUE(getMagnitude); + + rtl::function get_magnitude = getMagnitude->to().argsT().returnT(); + ASSERT_TRUE(get_magnitude); + + std::optional setReal = cxx::mirror().getFunction(str_complex, str_setReal); + ASSERT_TRUE(setReal); + + rtl::function set_real = setReal->to().argsT().returnT(); + ASSERT_TRUE(set_real); + + std::optional setImaginary = cxx::mirror().getFunction(str_complex, str_setImaginary); + ASSERT_TRUE(setImaginary); + + rtl::function set_imaginary = setImaginary->to().argsT().returnT(); + ASSERT_TRUE(set_imaginary); + + set_real(g_real); + set_imaginary(g_imaginary); + + double retVal = get_magnitude(); + + double magnitude = abs(std::complex(g_real, g_imaginary)); + + EXPECT_DOUBLE_EQ(magnitude, retVal); + } + + + TEST(StaticTypeQuery, global_function_execute_return) + { + std::optional getComplexNumAsString = cxx::mirror().getFunction(str_getComplexNumAsString); + ASSERT_TRUE(getComplexNumAsString); + { + rtl::function get_complex_num_as_string = getComplexNumAsString->to().argsT().returnT(); + ASSERT_FALSE(get_complex_num_as_string); + } { + rtl::function get_complex_num_as_string = getComplexNumAsString->to().argsT().returnT(); + ASSERT_FALSE(get_complex_num_as_string); + } { + rtl::function get_complex_num_as_string = getComplexNumAsString->to().argsT().returnT(); + ASSERT_TRUE(get_complex_num_as_string); + + std::string ret_str = get_complex_num_as_string(); + + std::string complex_num_str = std::to_string(g_real) + "i" + std::to_string(g_imaginary); + + EXPECT_EQ(complex_num_str, ret_str); + } + } + + + //TEST(StaticTypeQuery, overloaded_function_execute_return) + //{ + // std::optional reverseString = cxx::mirror().getFunction(str_reverseString); + // ASSERT_TRUE(reverseString); + // { + // //STRA's type is 'consexpr const char*', function accepts 'string', + // //so type-casting in place as 'string' + // auto [err, ret] = reverseString->bind().call(string(STRA)); + // EXPECT_TRUE(err == rtl::error::None); + // ASSERT_FALSE(ret.isEmpty()); + // EXPECT_TRUE(ret.canViewAs()); + + // string retVal = ret.view()->get(); + // EXPECT_TRUE(retVal == STRA_REVERSE); + // } { + // //STRB's type is 'consexpr const char*', function accepts 'string', + // //so explicitly binding type in template (using bind<...>()) to enforce the type as 'string'. + // auto [err, ret] = reverseString->bind().call(STRB); + + // EXPECT_TRUE(err == rtl::error::None); + // ASSERT_FALSE(ret.isEmpty()); + // EXPECT_TRUE(ret.canViewAs()); + + // string retVal = ret.view()->get(); + // EXPECT_TRUE(retVal == STRB_REVERSE); + // } { + // auto [err, ret] = reverseString->bind().call(); + // EXPECT_TRUE(err == rtl::error::None); + // ASSERT_FALSE(ret.isEmpty()); + // EXPECT_TRUE(ret.canViewAs()); + // + // string retVal = ret.view()->get(); + // EXPECT_TRUE(retVal == REV_STR_VOID_RET); + // } + //} + + + //TEST(Reflecting_STL_class, std_string__call_reflected_method) + //{ + // optional stdStringClass = cxx::mirror().getRecord("std", "string"); + // ASSERT_TRUE(stdStringClass); + + // optional isStringEmpty = stdStringClass->getMethod("empty"); + // ASSERT_TRUE(isStringEmpty); + + // RObject reflected_str0 = rtl::reflect(std::string("")); //empty string. + // { + // auto [err, ret] = isStringEmpty->bind(reflected_str0).call(); + // EXPECT_TRUE(err == rtl::error::None); + // ASSERT_FALSE(ret.isEmpty()); + // EXPECT_TRUE(ret.canViewAs()); + // EXPECT_TRUE(ret.view()->get()); + // } + // RObject reflected_str1 = rtl::reflect(std::string("not_empty")); + // { + // auto [err, ret] = isStringEmpty->bind(reflected_str1).call(); + // EXPECT_TRUE(err == rtl::error::None); + // ASSERT_FALSE(ret.isEmpty()); + // EXPECT_TRUE(ret.canViewAs()); + // EXPECT_FALSE(ret.view()->get()); + // } + //} + + + //TEST(Reflecting_STL_class, std_string_view__call_reflected_method) + //{ + // optional stdStringClass = cxx::mirror().getRecord("std", "string_view"); + // ASSERT_TRUE(stdStringClass); + + // optional isStringEmpty = stdStringClass->getMethod("empty"); + // ASSERT_TRUE(isStringEmpty); + + // RObject reflected_str0 = rtl::reflect(""); //empty string. + // { + // auto [err, ret] = isStringEmpty->bind(reflected_str0).call(); + // EXPECT_TRUE(err == rtl::error::None); + // ASSERT_FALSE(ret.isEmpty()); + // EXPECT_TRUE(ret.canViewAs()); + // EXPECT_TRUE(ret.view()->get()); + // } + // RObject reflected_str1 = rtl::reflect("not_empty"); + // { + // auto [err, ret] = isStringEmpty->bind(reflected_str1).call(); + // EXPECT_TRUE(err == rtl::error::None); + // ASSERT_FALSE(ret.isEmpty()); + // EXPECT_TRUE(ret.canViewAs()); + // EXPECT_FALSE(ret.view()->get()); + // } + //} +} \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h index ab3453a9..a1d1e89f 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.h @@ -16,7 +16,7 @@ namespace rtl::detail { template - struct FunctionCaller + struct ErasedCaller { const Function* m_function; diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index aa9f6822..f27edcea 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -18,15 +18,16 @@ #include "erased_function.h" + namespace rtl::detail { template template - ForceInline Return FunctionCaller<_signature...>::call(_args&&...params) const noexcept + ForceInline Return ErasedCaller<_signature...>::call(_args&&...params) const noexcept { using Container = std::conditional_t...>, - FunctorContainer<_signature...>>; + FunctorContainer...>, + FunctorContainer<_signature...>>; const detail::FunctorId* functorId = m_function->hasFunctorId(Container::getContainerId()); if (functorId != nullptr) [[likely]] { @@ -34,27 +35,31 @@ namespace rtl::detail } return { error::SignatureMismatch, RObject{} }; } +} - template - template - ForceInline constexpr Return FunctionCaller<_signature...>::operator()(_args&&...params) const noexcept + +namespace rtl::detail +{ + template + template + ForceInline constexpr Return ErasedCaller::operator()(argsT&&...params) const noexcept { - auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); + auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { const auto& erased = functorId->m_lambda->m_erasure; - const auto& caller = erased.template to_erased_ret_function<_args...>(); + const auto& caller = erased.template to_erased_ret_function(); if(functorId->m_lambda->is_void()) { - caller.hop_v(std::forward<_args>(params)...); + caller.hop_void(std::forward(params)...); return { error::None, RObject{} }; } else { return{ error::None, - RObject{ caller.hop_r(std::forward<_args>(params)...), - caller.get_return_robj_id(), nullptr } + RObject{ caller.hop_return(std::forward(params)...), + caller.get_return_id(), nullptr } }; } } @@ -65,30 +70,29 @@ namespace rtl::detail namespace rtl::detail { - template - inline constexpr const HopFunction<_signature...> Hopper<>::argsT() const + template + inline constexpr const HopFunction Hopper<>::argsT() const { - const auto argsId = TypeId... >>::get(); + const auto argsId = TypeId... >>::get(); for (auto& functorId : m_functorIds) { - auto lambda = functorId.get_lambda_function<_signature...>(argsId); + auto lambda = functorId.get_lambda_function(argsId); if (lambda != nullptr) [[likely]] { return { lambda }; } } - return HopFunction<_signature...>(); + return HopFunction(); } - template - template - inline constexpr const function<_returnType(_signature...)> - HopFunction<_signature...>::returnT() const + template + template + inline constexpr const function HopFunction::returnT() const { - const auto retId = TypeId<_returnType>::get(); + const auto retId = TypeId::get(); if (m_lambda != nullptr) [[likely]] { - return m_lambda->template get_hopper<_returnType>(retId); + return m_lambda->template get_hopper(retId); } - return function<_returnType(_signature...)>(); + return function(); } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index 284aedc1..884ba1e9 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -197,14 +197,14 @@ namespace rtl::detail const auto& caller = erased.template to_erased_ret_method<_recordType, _args...>(); if(functorId->m_lambda->is_void()) { - caller.hop_v(m_target, std::forward<_args>(params)...); + caller.hop_void(m_target, std::forward<_args>(params)...); return { error::None, RObject{} }; } else { return{ error::None, - RObject{ caller.hop_r(m_target, std::forward<_args>(params)...), - caller.get_return_robj_id(), nullptr } + RObject{ caller.hop_return(m_target, std::forward<_args>(params)...), + caller.get_return_id(), nullptr } }; } } @@ -223,14 +223,14 @@ namespace rtl::detail const auto& caller = erased.template to_erased_ret_function<_args...>(); if (functorId->m_lambda->is_void()) { - caller.hop_v(m_target, std::forward<_args>(params)...); + caller.hop_void(m_target, std::forward<_args>(params)...); return { error::None, RObject{} }; } else { return{ error::None, - RObject{ caller.hop_r(m_target, std::forward<_args>(params)...), - caller.get_return_robj_id(), nullptr } + RObject{ caller.hop_return(m_target, std::forward<_args>(params)...), + caller.get_return_id(), nullptr } }; } } diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h index f08071de..e06f0dab 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h @@ -30,7 +30,7 @@ namespace rtl } template - [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept // (noexcept_v) + [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept { //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (*m_functor)(std::forward(params)...); @@ -52,8 +52,5 @@ namespace rtl template static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - - //template - //static constexpr bool noexcept_v = noexcept(std::declval()(std::declval()...)); }; } diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h index 0f60353a..4316cdc9 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h @@ -31,7 +31,7 @@ namespace rtl } template - [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept //(noexcept_v) + [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept { //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (target.*m_functor)(std::forward(params)...); @@ -53,8 +53,5 @@ namespace rtl template static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - - //template - //static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h b/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h index b7e46b22..90175568 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h @@ -31,7 +31,7 @@ namespace rtl } template - [[nodiscard]] constexpr decltype(auto) operator()(const record_t& target, args_t&&...params) const noexcept//(noexcept_v) + [[nodiscard]] constexpr decltype(auto) operator()(const record_t& target, args_t&&...params) const noexcept { //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (target.*m_functor)(std::forward(params)...); @@ -53,8 +53,5 @@ namespace rtl template static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; - - //template - //static constexpr bool noexcept_v = noexcept((std::declval().*std::declval())(std::declval()...)); }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/erasure/erased_function.h b/ReflectionTemplateLib/rtl/erasure/erased_function.h index 749451eb..b55645c8 100644 --- a/ReflectionTemplateLib/rtl/erasure/erased_function.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_function.h @@ -19,22 +19,22 @@ namespace rtl::erase template struct erased_function : erasure_base { - constexpr void hop_v(signature_ts&&...params) const noexcept + constexpr void hop_void(signature_ts&&...params) const noexcept { (*hopper_v)(this, std::forward(params)...); } - ForceInline std::any hop_r(signature_ts&&...params) const noexcept + ForceInline std::any hop_return(signature_ts&&...params) const noexcept { return (*hopper_r)(this, std::forward(params)...); } - constexpr void hop_v(const RObject& p_robj, signature_ts&&...params) const noexcept + constexpr void hop_void(const RObject& p_robj, signature_ts&&...params) const noexcept { (*hopper_robj_v)(this, p_robj, std::forward(params)...); } - ForceInline std::any hop_r(const RObject& p_robj, signature_ts&&...params) const noexcept + ForceInline std::any hop_return(const RObject& p_robj, signature_ts&&...params) const noexcept { return (*hopper_robj_r)(this, p_robj, std::forward(params)...); } diff --git a/ReflectionTemplateLib/rtl/erasure/erased_method.h b/ReflectionTemplateLib/rtl/erasure/erased_method.h index 75101af2..39487f55 100644 --- a/ReflectionTemplateLib/rtl/erasure/erased_method.h +++ b/ReflectionTemplateLib/rtl/erasure/erased_method.h @@ -20,12 +20,12 @@ namespace rtl::erase template struct erased_method : erased_function { - constexpr void hop_v(const record_t& p_target, signature_ts&&...params) const noexcept + constexpr void hop_void(const record_t& p_target, signature_ts&&...params) const noexcept { (*hopper_v)(this, p_target, std::forward(params)...); } - ForceInline std::any hop_r(const record_t& p_target, signature_ts&&...params) const noexcept + ForceInline std::any hop_return(const record_t& p_target, signature_ts&&...params) const noexcept { return (*hopper_r)(this, p_target, std::forward(params)...); } diff --git a/ReflectionTemplateLib/rtl/erasure/erasure.h b/ReflectionTemplateLib/rtl/erasure/erasure.h index 02001436..cb001113 100644 --- a/ReflectionTemplateLib/rtl/erasure/erasure.h +++ b/ReflectionTemplateLib/rtl/erasure/erasure.h @@ -38,13 +38,13 @@ namespace rtl::erase erasure_base(const dispatch::functor& p_functor, const detail::RObjectId& p_robj_id) noexcept : m_functor(p_functor) - , m_ret_obj_id(p_robj_id) + , m_robj_id(p_robj_id) { } const dispatch::functor& m_functor; - const detail::RObjectId m_ret_obj_id; + const detail::RObjectId m_robj_id; - GETTER(detail::RObjectId, _return_robj_id, m_ret_obj_id); + GETTER(detail::RObjectId, _return_id, m_robj_id); }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 6edd8c0d..8ba3bb43 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -88,23 +88,26 @@ namespace rtl { Function& operator=(Function&&) = default; Function& operator=(const Function&) = default; - constexpr detail::Hopper<> lambda() const; + constexpr detail::Hopper<> to() const; bool hasSignature() const; template bool hasSignature() const; - template - constexpr const detail::FunctionCaller<_args...> operator()(_args&&...params) const noexcept; - template - constexpr const detail::FunctionCaller<_signature...> bind() const noexcept; + constexpr const detail::ErasedCaller<_signature...> bind() const noexcept; + + template + constexpr rtl::Return operator()(_args&&...params) const noexcept + { + return detail::ErasedCaller<_args...>{ this }(std::forward<_args>(params)...); + } friend detail::CxxReflection; friend detail::ReflectionBuilder; template - friend class detail::FunctionCaller; + friend class detail::ErasedCaller; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index 77dd5ec1..e63053eb 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -21,13 +21,13 @@ namespace rtl { template - inline constexpr const detail::FunctionCaller<_signature...> Function::bind() const noexcept + inline constexpr const detail::ErasedCaller<_signature...> Function::bind() const noexcept { - return detail::FunctionCaller<_signature...>{ this }; + return detail::ErasedCaller<_signature...>{ this }; } - inline constexpr detail::Hopper<> Function::lambda() const + inline constexpr detail::Hopper<> Function::to() const { return detail::Hopper<>{ m_functorIds }; } @@ -45,18 +45,6 @@ namespace rtl } -/* @method: operator()() - @param: variadic arguments. - @return: Return, possible error & return value of from the reflected call. - * if the arguments did not match with any overload, returns RObject with error::SignatureMismatch - * providing optional syntax, Function::call() does the exact same thing. -*/ template - inline constexpr const detail::FunctionCaller<_args...> Function::operator()(_args&& ...params) const noexcept - { - return detail::FunctionCaller<_args...>{ this }; - } - - /* @method: hasSignatureId() @param: const std::size_t& (signatureId to be found) @return: the index of the functor in the functor-table. diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index 343cf22e..ba2cdde8 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -54,12 +54,12 @@ namespace rtl { using Function::bind; template - constexpr const detail::FunctionCaller<_args...> operator()(_args&&...params) const noexcept = delete; + constexpr const detail::ErasedCaller<_args...> operator()(_args&&...params) const noexcept = delete; GETTER_BOOL(Const, (getQualifier() == detail::methodQ::Const)); template - constexpr detail::Hopper<_recordType> lambda() const; + constexpr detail::Hopper<_recordType> to() const; //indicates if a particular set of arguments accepted by the functor associated with it. template diff --git a/ReflectionTemplateLib/rtl/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp index 9e63f222..b415685d 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.hpp +++ b/ReflectionTemplateLib/rtl/inc/Method.hpp @@ -30,7 +30,7 @@ namespace rtl template - inline constexpr detail::Hopper<_recordType> Method::lambda() const + inline constexpr detail::Hopper<_recordType> Method::to() const { return detail::Hopper<_recordType>{ getFunctorIds() }; } diff --git a/ReflectionTemplateLib/rtl/inc/RObject.h b/ReflectionTemplateLib/rtl/inc/RObject.h index b3b6a27a..a0e597aa 100644 --- a/ReflectionTemplateLib/rtl/inc/RObject.h +++ b/ReflectionTemplateLib/rtl/inc/RObject.h @@ -107,7 +107,7 @@ namespace rtl friend struct detail::RObjectBuilder; template - friend struct detail::FunctionCaller; + friend struct detail::ErasedCaller; template friend struct detail::ErasedInvoker; diff --git a/ReflectionTemplateLib/rtl/rtl_forward_decls.h b/ReflectionTemplateLib/rtl/rtl_forward_decls.h index 08b1f8ac..9febcad4 100644 --- a/ReflectionTemplateLib/rtl/rtl_forward_decls.h +++ b/ReflectionTemplateLib/rtl/rtl_forward_decls.h @@ -54,7 +54,7 @@ namespace rtl class FunctorContainer; template - struct FunctionCaller; + struct ErasedCaller; template struct ErasedInvoker; From 551443eccb3274c03de6c291dffa2a7578812457 Mon Sep 17 00:00:00 2001 From: neeraj Date: Sat, 4 Oct 2025 00:42:55 +0530 Subject: [PATCH 56/58] fix gcc/clang compile error. --- ReflectionTemplateLib/rtl/inc/Function.h | 1 + 1 file changed, 1 insertion(+) diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 8ba3bb43..18f505af 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -15,6 +15,7 @@ #include #include +#include "RObject.h" #include "FunctionCaller.h" namespace rtl { From 9a58d1ad1ede7743c481b272fefcda9ceaaa6d07 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Sat, 4 Oct 2025 17:43:27 +0530 Subject: [PATCH 57/58] static-dispatch test cases, const-method resolution. --- .../src/ReflectedCallKnownReturn.cpp | 8 +- .../StaticTypeCFunctionTests.cpp | 185 ++++++++---------- .../rtl/detail/inc/MethodInvoker.h | 17 +- .../rtl/detail/inc/MethodInvoker.hpp | 66 ++++--- .../rtl/dispatch/rtl_function.h | 4 - .../rtl/dispatch/rtl_method.h | 4 - .../rtl/dispatch/rtl_method_const.h | 4 - ReflectionTemplateLib/rtl/inc/Function.h | 3 +- ReflectionTemplateLib/rtl/inc/Function.hpp | 7 +- ReflectionTemplateLib/rtl/inc/Method.h | 9 +- ReflectionTemplateLib/rtl/inc/Method.hpp | 6 +- 11 files changed, 152 insertions(+), 161 deletions(-) diff --git a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp index 4d17b05c..cd0c36fd 100644 --- a/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp +++ b/RTLBenchmarkApp/src/ReflectedCallKnownReturn.cpp @@ -28,7 +28,7 @@ namespace std::cerr << "[00] error: erase_function 'getMessage' not found."; std::abort(); } - return function->to().argsT().returnT(); + return function->argsT().returnT(); }(); static const rtl::function sendMessage = []() @@ -39,7 +39,7 @@ namespace std::cerr << "[01] error: erase_function 'sendMessage' not found."; std::abort(); } - return function->to().argsT().returnT(); + return function->argsT().returnT(); }(); static const rtl::method getMessageNode = []() @@ -55,7 +55,7 @@ namespace std::cerr << "[02] error: method 'Node::getMessage' not found."; std::abort(); } - return method->to().argsT().returnT(); + return method->recordT().argsT().returnT(); }(); static const rtl::method sendMessageNode = []() @@ -71,7 +71,7 @@ namespace std::cerr << "[3] error: method 'Node::sendMessage' not found."; std::abort(); } - return method->to().argsT().returnT(); + return method->recordT().argsT().returnT(); }(); } diff --git a/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp b/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp index 51c7d0cd..7a561d38 100644 --- a/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp +++ b/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp @@ -11,7 +11,7 @@ using namespace test_mirror; namespace rtl_tests { - TEST(StaticTypeQuery, get_namespace_function_types) + TEST(StaticTypeFunctionQuery, function_validation_with_given_signature) { std::optional setReal = cxx::mirror().getFunction(str_complex, str_setReal); ASSERT_TRUE(setReal); @@ -19,10 +19,10 @@ namespace rtl_tests EXPECT_TRUE(setReal->getNamespace() == str_complex); EXPECT_TRUE(setReal->getFunctionName() == str_setReal); { - rtl::function functor = setReal->to().argsT().returnT(); + rtl::function functor = setReal->argsT().returnT(); ASSERT_TRUE(functor); } { - rtl::function functor = setReal->to().argsT().returnT(); + rtl::function functor = setReal->argsT().returnT(); ASSERT_FALSE(functor); } } @@ -33,34 +33,34 @@ namespace rtl_tests EXPECT_TRUE(setImaginary->getNamespace() == str_complex); EXPECT_TRUE(setImaginary->getFunctionName() == str_setImaginary); { - rtl::function functor = setImaginary->to().argsT().returnT(); + rtl::function functor = setImaginary->argsT().returnT(); ASSERT_TRUE(functor); } { - rtl::function functor = setImaginary->to().argsT().returnT(); + rtl::function functor = setImaginary->argsT().returnT(); ASSERT_FALSE(functor); } } } - TEST(StaticTypeQuery, namespace_function_execute_return) + TEST(StaticTypeFunctionQuery, function_executation_with_given_signature) { std::optional getMagnitude = cxx::mirror().getFunction(str_complex, str_getMagnitude); ASSERT_TRUE(getMagnitude); - rtl::function get_magnitude = getMagnitude->to().argsT().returnT(); + rtl::function get_magnitude = getMagnitude->argsT<>().returnT(); ASSERT_TRUE(get_magnitude); std::optional setReal = cxx::mirror().getFunction(str_complex, str_setReal); ASSERT_TRUE(setReal); - rtl::function set_real = setReal->to().argsT().returnT(); + rtl::function set_real = setReal->argsT().returnT(); ASSERT_TRUE(set_real); std::optional setImaginary = cxx::mirror().getFunction(str_complex, str_setImaginary); ASSERT_TRUE(setImaginary); - rtl::function set_imaginary = setImaginary->to().argsT().returnT(); + rtl::function set_imaginary = setImaginary->argsT().returnT(); ASSERT_TRUE(set_imaginary); set_real(g_real); @@ -74,18 +74,18 @@ namespace rtl_tests } - TEST(StaticTypeQuery, global_function_execute_return) + TEST(StaticTypeFunctionQuery, global_function_executation_with_given_signature) { std::optional getComplexNumAsString = cxx::mirror().getFunction(str_getComplexNumAsString); ASSERT_TRUE(getComplexNumAsString); { - rtl::function get_complex_num_as_string = getComplexNumAsString->to().argsT().returnT(); + rtl::function get_complex_num_as_string = getComplexNumAsString->argsT<>().returnT(); ASSERT_FALSE(get_complex_num_as_string); } { - rtl::function get_complex_num_as_string = getComplexNumAsString->to().argsT().returnT(); + rtl::function get_complex_num_as_string = getComplexNumAsString->argsT<>().returnT(); ASSERT_FALSE(get_complex_num_as_string); } { - rtl::function get_complex_num_as_string = getComplexNumAsString->to().argsT().returnT(); + rtl::function get_complex_num_as_string = getComplexNumAsString->argsT<>().returnT(); ASSERT_TRUE(get_complex_num_as_string); std::string ret_str = get_complex_num_as_string(); @@ -97,93 +97,74 @@ namespace rtl_tests } - //TEST(StaticTypeQuery, overloaded_function_execute_return) - //{ - // std::optional reverseString = cxx::mirror().getFunction(str_reverseString); - // ASSERT_TRUE(reverseString); - // { - // //STRA's type is 'consexpr const char*', function accepts 'string', - // //so type-casting in place as 'string' - // auto [err, ret] = reverseString->bind().call(string(STRA)); - // EXPECT_TRUE(err == rtl::error::None); - // ASSERT_FALSE(ret.isEmpty()); - // EXPECT_TRUE(ret.canViewAs()); - - // string retVal = ret.view()->get(); - // EXPECT_TRUE(retVal == STRA_REVERSE); - // } { - // //STRB's type is 'consexpr const char*', function accepts 'string', - // //so explicitly binding type in template (using bind<...>()) to enforce the type as 'string'. - // auto [err, ret] = reverseString->bind().call(STRB); - - // EXPECT_TRUE(err == rtl::error::None); - // ASSERT_FALSE(ret.isEmpty()); - // EXPECT_TRUE(ret.canViewAs()); - - // string retVal = ret.view()->get(); - // EXPECT_TRUE(retVal == STRB_REVERSE); - // } { - // auto [err, ret] = reverseString->bind().call(); - // EXPECT_TRUE(err == rtl::error::None); - // ASSERT_FALSE(ret.isEmpty()); - // EXPECT_TRUE(ret.canViewAs()); - // - // string retVal = ret.view()->get(); - // EXPECT_TRUE(retVal == REV_STR_VOID_RET); - // } - //} - - - //TEST(Reflecting_STL_class, std_string__call_reflected_method) - //{ - // optional stdStringClass = cxx::mirror().getRecord("std", "string"); - // ASSERT_TRUE(stdStringClass); - - // optional isStringEmpty = stdStringClass->getMethod("empty"); - // ASSERT_TRUE(isStringEmpty); - - // RObject reflected_str0 = rtl::reflect(std::string("")); //empty string. - // { - // auto [err, ret] = isStringEmpty->bind(reflected_str0).call(); - // EXPECT_TRUE(err == rtl::error::None); - // ASSERT_FALSE(ret.isEmpty()); - // EXPECT_TRUE(ret.canViewAs()); - // EXPECT_TRUE(ret.view()->get()); - // } - // RObject reflected_str1 = rtl::reflect(std::string("not_empty")); - // { - // auto [err, ret] = isStringEmpty->bind(reflected_str1).call(); - // EXPECT_TRUE(err == rtl::error::None); - // ASSERT_FALSE(ret.isEmpty()); - // EXPECT_TRUE(ret.canViewAs()); - // EXPECT_FALSE(ret.view()->get()); - // } - //} - - - //TEST(Reflecting_STL_class, std_string_view__call_reflected_method) - //{ - // optional stdStringClass = cxx::mirror().getRecord("std", "string_view"); - // ASSERT_TRUE(stdStringClass); - - // optional isStringEmpty = stdStringClass->getMethod("empty"); - // ASSERT_TRUE(isStringEmpty); - - // RObject reflected_str0 = rtl::reflect(""); //empty string. - // { - // auto [err, ret] = isStringEmpty->bind(reflected_str0).call(); - // EXPECT_TRUE(err == rtl::error::None); - // ASSERT_FALSE(ret.isEmpty()); - // EXPECT_TRUE(ret.canViewAs()); - // EXPECT_TRUE(ret.view()->get()); - // } - // RObject reflected_str1 = rtl::reflect("not_empty"); - // { - // auto [err, ret] = isStringEmpty->bind(reflected_str1).call(); - // EXPECT_TRUE(err == rtl::error::None); - // ASSERT_FALSE(ret.isEmpty()); - // EXPECT_TRUE(ret.canViewAs()); - // EXPECT_FALSE(ret.view()->get()); - // } - //} + TEST(StaticTypeFunctionQuery, function_overload_resolution_with_given_signature) + { + std::optional reverseString = cxx::mirror().getFunction(str_reverseString); + ASSERT_TRUE(reverseString); + { + rtl::function reverse_string = reverseString->argsT().returnT(); + ASSERT_TRUE(reverse_string); + + std::string ret_str = reverse_string(STRA); + EXPECT_EQ(ret_str, STRA_REVERSE); + } { + rtl::function reverse_string = reverseString->argsT().returnT(); + ASSERT_TRUE(reverse_string); + + std::string ret_str = reverse_string(STRB); + EXPECT_EQ(ret_str, STRB_REVERSE); + } { + rtl::function reverse_string = reverseString->argsT<>().returnT(); + ASSERT_TRUE(reverse_string); + + std::string ret_str = reverse_string(); + EXPECT_EQ(ret_str, REV_STR_VOID_RET); + } + } + + + TEST(StaticTypeMethodQuery, std_string_call_reflected_method_empty) + { + std::optional stdStringClass = cxx::mirror().getRecord("std", "string"); + ASSERT_TRUE(stdStringClass); + + std::optional isStringEmpty = stdStringClass->getMethod("empty"); + ASSERT_TRUE(isStringEmpty); + + rtl::method is_empty = isStringEmpty->recordT().argsT<>().returnT(); + ASSERT_TRUE(is_empty); + + EXPECT_TRUE(is_empty(std::string(""))); + + EXPECT_FALSE(is_empty(std::string("not_empty"))); + + EXPECT_TRUE(is_empty("")); + + EXPECT_FALSE(is_empty("view_not_empty")); + } + + + TEST(StaticTypeMethodQuery, std_string_view_call_reflected_method_empty) + { + std::optional stdStringViewClass = cxx::mirror().getRecord("std", "string_view"); + ASSERT_TRUE(stdStringViewClass); + + std::optional isStringEmpty = stdStringViewClass->getMethod("empty"); + ASSERT_TRUE(isStringEmpty); + + rtl::method is_empty = isStringEmpty->recordT().argsT<>().returnT(); + ASSERT_TRUE(is_empty); + + EXPECT_TRUE(is_empty(std::string(""))); + + EXPECT_FALSE(is_empty(std::string("not_empty"))); + + EXPECT_TRUE(is_empty(std::string_view(""))); + + EXPECT_FALSE(is_empty(std::string_view("view_not_empty"))); + + EXPECT_TRUE(is_empty("")); + + EXPECT_FALSE(is_empty("view_not_empty")); + } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h index 55f9d9f9..2b7d0dd1 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.h @@ -89,21 +89,24 @@ namespace rtl::detail { namespace rtl::detail { - template + template struct HopMethod { - const dispatch::lambda_method<_recordType, _signature...>* m_lambda = nullptr; + const dispatch::lambda_method* m_lambda = nullptr; - template - constexpr const method<_returnType(_recordType::*)(_signature...)> returnT() const; + template requires (std::is_const_v == false) + constexpr const method returnT() const; + + template requires (std::is_const_v == true) + constexpr const method returnT() const; }; - template + template struct Hopper { const std::vector& m_functorIds; - template - constexpr HopMethod<_recordType, _signature...> argsT() const; + template + constexpr HopMethod argsT() const; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index 884ba1e9..bfd6beef 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -152,58 +152,72 @@ namespace rtl::detail namespace rtl::detail { - template - template - inline constexpr HopMethod<_recordType, _signature...> Hopper<_recordType>::argsT() const + template + template + inline constexpr HopMethod Hopper::argsT() const { - const auto recId = TypeId<_recordType>::get(); - const auto argsId = TypeId...>>::get(); + const auto recId = TypeId::get(); + const auto argsId = TypeId...>>::get(); for (auto& functorId : m_functorIds) { - auto lambda = functorId.get_lambda_method<_recordType, _signature...>(recId, argsId); + auto lambda = functorId.get_lambda_method(recId, argsId); if (lambda != nullptr) [[likely]] { return { lambda }; } } - return HopMethod<_recordType, _signature...>(); + return HopMethod(); + } + + + template + template requires (std::is_const_v == false) + inline constexpr const method<_returnType(recordT::*)(signatureT...)> + HopMethod::returnT() const + { + if (m_lambda != nullptr) [[likely]] + { + const auto retId = TypeId<_returnType>::get(); + return m_lambda->template get_hopper<_returnType>(retId); + } + return method<_returnType(recordT::*)(signatureT...)>(); } - template - template - inline constexpr const method<_returnType(_recordType::*)(_signature...)> - HopMethod<_recordType, _signature...>::returnT() const + template + template requires (std::is_const_v == true) + inline constexpr const method<_returnType(recordT::*)(signatureT...) const> + HopMethod::returnT() const { if (m_lambda != nullptr) [[likely]] { const auto retId = TypeId<_returnType>::get(); return m_lambda->template get_hopper<_returnType>(retId); } - return method<_returnType(_recordType::*)(_signature...)>(); + return method<_returnType(recordT::*)(signatureT...) const>(); } } namespace rtl::detail { - template - template requires (std::is_same_v, RObject> == false) - ForceInline constexpr Return ErasedInvoker<_recordType>::operator()(_args&&...params) const noexcept + template + template requires (std::is_same_v, RObject> == false) + ForceInline constexpr Return ErasedInvoker::operator()(argsT&&...params) const noexcept { - auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); + auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { const auto& erased = functorId->m_lambda->m_erasure; - const auto& caller = erased.template to_erased_ret_method<_recordType, _args...>(); + const auto& caller = erased.template to_erased_ret_method(); if(functorId->m_lambda->is_void()) { - caller.hop_void(m_target, std::forward<_args>(params)...); + caller.hop_void(m_target, std::forward(params)...); return { error::None, RObject{} }; } else { return{ error::None, - RObject{ caller.hop_return(m_target, std::forward<_args>(params)...), + RObject{ caller.hop_return(m_target, std::forward(params)...), caller.get_return_id(), nullptr } }; } @@ -212,24 +226,24 @@ namespace rtl::detail } - template - template requires (std::is_same_v, RObject> == true) - ForceInline constexpr Return ErasedInvoker<_recordType>::operator()(_args&&...params) const noexcept + template + template requires (std::is_same_v, RObject> == true) + ForceInline constexpr Return ErasedInvoker::operator()(argsT&&...params) const noexcept { - auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); + auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); if (functorId) [[likely]] { const auto& erased = functorId->m_lambda->m_erasure; - const auto& caller = erased.template to_erased_ret_function<_args...>(); + const auto& caller = erased.template to_erased_ret_function(); if (functorId->m_lambda->is_void()) { - caller.hop_void(m_target, std::forward<_args>(params)...); + caller.hop_void(m_target, std::forward(params)...); return { error::None, RObject{} }; } else { return{ error::None, - RObject{ caller.hop_return(m_target, std::forward<_args>(params)...), + RObject{ caller.hop_return(m_target, std::forward(params)...), caller.get_return_id(), nullptr } }; } diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h index e06f0dab..7470998b 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_function.h @@ -32,7 +32,6 @@ namespace rtl template [[nodiscard]] constexpr decltype(auto) operator()(args_t&&...params) const noexcept { - //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (*m_functor)(std::forward(params)...); } @@ -49,8 +48,5 @@ namespace rtl private: fptr_t m_functor = nullptr; - - template - static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; }; } diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h index 4316cdc9..3ccc65da 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_method.h @@ -33,7 +33,6 @@ namespace rtl template [[nodiscard]] constexpr decltype(auto) operator()(record_t& target, args_t&&...params) const noexcept { - //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (target.*m_functor)(std::forward(params)...); } @@ -50,8 +49,5 @@ namespace rtl private: fptr_t m_functor = nullptr; - - template - static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h b/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h index 90175568..d7a467ff 100644 --- a/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h +++ b/ReflectionTemplateLib/rtl/dispatch/rtl_method_const.h @@ -33,7 +33,6 @@ namespace rtl template [[nodiscard]] constexpr decltype(auto) operator()(const record_t& target, args_t&&...params) const noexcept { - //static_assert(is_args_t_ok, "Argument types don't match the expected signature."); return (target.*m_functor)(std::forward(params)...); } @@ -50,8 +49,5 @@ namespace rtl private: fptr_t m_functor = nullptr; - - template - static constexpr bool is_args_t_ok = std::is_same_v...>, std::tuple>; }; } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/inc/Function.h b/ReflectionTemplateLib/rtl/inc/Function.h index 8ba3bb43..f6f70f2d 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.h +++ b/ReflectionTemplateLib/rtl/inc/Function.h @@ -88,7 +88,8 @@ namespace rtl { Function& operator=(Function&&) = default; Function& operator=(const Function&) = default; - constexpr detail::Hopper<> to() const; + template + constexpr const detail::HopFunction argsT() const; bool hasSignature() const; diff --git a/ReflectionTemplateLib/rtl/inc/Function.hpp b/ReflectionTemplateLib/rtl/inc/Function.hpp index e63053eb..b01f23c1 100644 --- a/ReflectionTemplateLib/rtl/inc/Function.hpp +++ b/ReflectionTemplateLib/rtl/inc/Function.hpp @@ -26,12 +26,13 @@ namespace rtl return detail::ErasedCaller<_signature...>{ this }; } - - inline constexpr detail::Hopper<> Function::to() const + template + inline constexpr const detail::HopFunction Function::argsT() const { - return detail::Hopper<>{ m_functorIds }; + return detail::Hopper<>{ m_functorIds }.argsT(); } + /* @method: hasSignature<...>() @param: set of arguments, explicitly specified as template parameter. @return: bool, if the functor associated with this object is of certain signature or not. diff --git a/ReflectionTemplateLib/rtl/inc/Method.h b/ReflectionTemplateLib/rtl/inc/Method.h index ba2cdde8..9e746680 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.h +++ b/ReflectionTemplateLib/rtl/inc/Method.h @@ -51,15 +51,18 @@ namespace rtl { Method& operator=(Method&&) = default; Method& operator=(const Method&) = default; + GETTER_BOOL(Const, (getQualifier() == detail::methodQ::Const)); + using Function::bind; template constexpr const detail::ErasedCaller<_args...> operator()(_args&&...params) const noexcept = delete; - GETTER_BOOL(Const, (getQualifier() == detail::methodQ::Const)); + template + constexpr const detail::HopFunction argsT() const = delete; - template - constexpr detail::Hopper<_recordType> to() const; + template + constexpr detail::Hopper recordT() const; //indicates if a particular set of arguments accepted by the functor associated with it. template diff --git a/ReflectionTemplateLib/rtl/inc/Method.hpp b/ReflectionTemplateLib/rtl/inc/Method.hpp index b415685d..7f0ae7e6 100644 --- a/ReflectionTemplateLib/rtl/inc/Method.hpp +++ b/ReflectionTemplateLib/rtl/inc/Method.hpp @@ -29,10 +29,10 @@ namespace rtl } - template - inline constexpr detail::Hopper<_recordType> Method::to() const + template + inline constexpr detail::Hopper Method::recordT() const { - return detail::Hopper<_recordType>{ getFunctorIds() }; + return detail::Hopper{ getFunctorIds() }; } From 491cfed8d88abc400a075e8a24a7e2bc41af9f93 Mon Sep 17 00:00:00 2001 From: neeraj31285 Date: Sat, 4 Oct 2025 23:59:32 +0530 Subject: [PATCH 58/58] strict-type-matching for static-typed dispatch, tests. --- RTLTestRunApp/src/CMakeLists.txt | 1 + ...Tests.cpp => StrictStaticTypeDispatch.cpp} | 75 +++++++++++-------- .../rtl/detail/inc/FunctionCaller.hpp | 4 +- .../rtl/detail/inc/MethodInvoker.hpp | 6 +- .../rtl/dispatch/functor_function.h | 2 +- .../rtl/dispatch/functor_method.h | 2 +- .../rtl/dispatch/functor_method_const.h | 2 +- ReflectionTemplateLib/rtl/rtl_traits.h | 10 +++ 8 files changed, 62 insertions(+), 40 deletions(-) rename RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/{StaticTypeCFunctionTests.cpp => StrictStaticTypeDispatch.cpp} (59%) diff --git a/RTLTestRunApp/src/CMakeLists.txt b/RTLTestRunApp/src/CMakeLists.txt index 5e0400f4..81ec3ddd 100644 --- a/RTLTestRunApp/src/CMakeLists.txt +++ b/RTLTestRunApp/src/CMakeLists.txt @@ -16,6 +16,7 @@ set(LOCAL_SOURCES_0 "${CMAKE_CURRENT_LIST_DIR}/FunctionalityTests/PerfectForwardingTests.cpp" "${CMAKE_CURRENT_LIST_DIR}/FunctionalityTests/MoveConstructorTests.cpp" "${CMAKE_CURRENT_LIST_DIR}/FunctionalityTests/ReturnValueReflectionTest.cpp" + "${CMAKE_CURRENT_LIST_DIR}/FunctionalityTests/StaticTypeReflectiveCalls/StrictStaticTypeDispatch.cpp" ) # Create a variable containing the source files for your target diff --git a/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp b/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StrictStaticTypeDispatch.cpp similarity index 59% rename from RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp rename to RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StrictStaticTypeDispatch.cpp index 7a561d38..2ade857f 100644 --- a/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StaticTypeCFunctionTests.cpp +++ b/RTLTestRunApp/src/FunctionalityTests/StaticTypeReflectiveCalls/StrictStaticTypeDispatch.cpp @@ -11,7 +11,7 @@ using namespace test_mirror; namespace rtl_tests { - TEST(StaticTypeFunctionQuery, function_validation_with_given_signature) + TEST(StrictStaticTypeDispatch, namespace_function_validation_with_known_signature) { std::optional setReal = cxx::mirror().getFunction(str_complex, str_setReal); ASSERT_TRUE(setReal); @@ -43,7 +43,7 @@ namespace rtl_tests } - TEST(StaticTypeFunctionQuery, function_executation_with_given_signature) + TEST(StrictStaticTypeDispatch, namespace_function_call_with_known_signature) { std::optional getMagnitude = cxx::mirror().getFunction(str_complex, str_getMagnitude); ASSERT_TRUE(getMagnitude); @@ -74,21 +74,21 @@ namespace rtl_tests } - TEST(StaticTypeFunctionQuery, global_function_executation_with_given_signature) + TEST(StrictStaticTypeDispatch, global_function_call_with_known_signature) { - std::optional getComplexNumAsString = cxx::mirror().getFunction(str_getComplexNumAsString); - ASSERT_TRUE(getComplexNumAsString); + std::optional getComplexNumStr = cxx::mirror().getFunction(str_getComplexNumAsString); + ASSERT_TRUE(getComplexNumStr); { - rtl::function get_complex_num_as_string = getComplexNumAsString->argsT<>().returnT(); - ASSERT_FALSE(get_complex_num_as_string); + rtl::function get_complex_num_str = getComplexNumStr->argsT<>().returnT(); + ASSERT_FALSE(get_complex_num_str); } { - rtl::function get_complex_num_as_string = getComplexNumAsString->argsT<>().returnT(); - ASSERT_FALSE(get_complex_num_as_string); + rtl::function get_complex_num_str = getComplexNumStr->argsT<>().returnT(); + ASSERT_FALSE(get_complex_num_str); } { - rtl::function get_complex_num_as_string = getComplexNumAsString->argsT<>().returnT(); - ASSERT_TRUE(get_complex_num_as_string); + rtl::function get_complex_num_str = getComplexNumStr->argsT<>().returnT(); + ASSERT_TRUE(get_complex_num_str); - std::string ret_str = get_complex_num_as_string(); + std::string ret_str = get_complex_num_str(); std::string complex_num_str = std::to_string(g_real) + "i" + std::to_string(g_imaginary); @@ -97,12 +97,15 @@ namespace rtl_tests } - TEST(StaticTypeFunctionQuery, function_overload_resolution_with_given_signature) + TEST(StrictStaticTypeDispatch, overload_resolution_with_known_signatures) { std::optional reverseString = cxx::mirror().getFunction(str_reverseString); ASSERT_TRUE(reverseString); { - rtl::function reverse_string = reverseString->argsT().returnT(); + rtl::function reverse_string = reverseString->argsT().returnT(); + ASSERT_FALSE(reverse_string); + } { + rtl::function reverse_string = reverseString->argsT().returnT(); ASSERT_TRUE(reverse_string); std::string ret_str = reverse_string(STRA); @@ -123,48 +126,56 @@ namespace rtl_tests } - TEST(StaticTypeMethodQuery, std_string_call_reflected_method_empty) + TEST(StrictStaticTypeDispatch, std_string_method_call_with_known_signature) { std::optional stdStringClass = cxx::mirror().getRecord("std", "string"); ASSERT_TRUE(stdStringClass); std::optional isStringEmpty = stdStringClass->getMethod("empty"); ASSERT_TRUE(isStringEmpty); + { + rtl::method is_empty = isStringEmpty->recordT().argsT<>().returnT(); + ASSERT_FALSE(is_empty); + } { + rtl::method is_empty = isStringEmpty->recordT().argsT<>().returnT(); + ASSERT_TRUE(is_empty); - rtl::method is_empty = isStringEmpty->recordT().argsT<>().returnT(); - ASSERT_TRUE(is_empty); - - EXPECT_TRUE(is_empty(std::string(""))); + EXPECT_TRUE(is_empty(std::string(""))); - EXPECT_FALSE(is_empty(std::string("not_empty"))); + EXPECT_FALSE(is_empty(std::string("not_empty"))); - EXPECT_TRUE(is_empty("")); + EXPECT_TRUE(is_empty("")); - EXPECT_FALSE(is_empty("view_not_empty")); + EXPECT_FALSE(is_empty("view_not_empty")); + } } - TEST(StaticTypeMethodQuery, std_string_view_call_reflected_method_empty) + TEST(StrictStaticTypeDispatch, std_string_view_method_call_with_known_signature) { std::optional stdStringViewClass = cxx::mirror().getRecord("std", "string_view"); ASSERT_TRUE(stdStringViewClass); std::optional isStringEmpty = stdStringViewClass->getMethod("empty"); ASSERT_TRUE(isStringEmpty); + { + rtl::method is_empty = isStringEmpty->recordT().argsT<>().returnT(); + ASSERT_FALSE(is_empty); + } { + rtl::method is_empty = isStringEmpty->recordT().argsT<>().returnT(); + ASSERT_TRUE(is_empty); - rtl::method is_empty = isStringEmpty->recordT().argsT<>().returnT(); - ASSERT_TRUE(is_empty); - - EXPECT_TRUE(is_empty(std::string(""))); + EXPECT_TRUE(is_empty(std::string(""))); - EXPECT_FALSE(is_empty(std::string("not_empty"))); + EXPECT_FALSE(is_empty(std::string("not_empty"))); - EXPECT_TRUE(is_empty(std::string_view(""))); + EXPECT_TRUE(is_empty(std::string_view(""))); - EXPECT_FALSE(is_empty(std::string_view("view_not_empty"))); + EXPECT_FALSE(is_empty(std::string_view("view_not_empty"))); - EXPECT_TRUE(is_empty("")); + EXPECT_TRUE(is_empty("")); - EXPECT_FALSE(is_empty("view_not_empty")); + EXPECT_FALSE(is_empty("view_not_empty")); + } } } \ No newline at end of file diff --git a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp index f27edcea..9d8b9635 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/FunctionCaller.hpp @@ -45,7 +45,7 @@ namespace rtl::detail template ForceInline constexpr Return ErasedCaller::operator()(argsT&&...params) const noexcept { - auto functorId = m_function->getLambdaById(detail::TypeId... >>::get()); + auto functorId = m_function->getLambdaById(detail::TypeId>::get()); if (functorId) [[likely]] { const auto& erased = functorId->m_lambda->m_erasure; @@ -73,7 +73,7 @@ namespace rtl::detail template inline constexpr const HopFunction Hopper<>::argsT() const { - const auto argsId = TypeId... >>::get(); + const auto argsId = TypeId>::get(); for (auto& functorId : m_functorIds) { auto lambda = functorId.get_lambda_function(argsId); diff --git a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp index bfd6beef..67a9c4d5 100644 --- a/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp +++ b/ReflectionTemplateLib/rtl/detail/inc/MethodInvoker.hpp @@ -157,7 +157,7 @@ namespace rtl::detail inline constexpr HopMethod Hopper::argsT() const { const auto recId = TypeId::get(); - const auto argsId = TypeId...>>::get(); + const auto argsId = TypeId>::get(); for (auto& functorId : m_functorIds) { auto lambda = functorId.get_lambda_method(recId, argsId); @@ -204,7 +204,7 @@ namespace rtl::detail template requires (std::is_same_v, RObject> == false) ForceInline constexpr Return ErasedInvoker::operator()(argsT&&...params) const noexcept { - auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); + auto functorId = m_method.getLambdaById(detail::TypeId>::get()); if (functorId) [[likely]] { const auto& erased = functorId->m_lambda->m_erasure; @@ -230,7 +230,7 @@ namespace rtl::detail template requires (std::is_same_v, RObject> == true) ForceInline constexpr Return ErasedInvoker::operator()(argsT&&...params) const noexcept { - auto functorId = m_method.getLambdaById(detail::TypeId... >>::get()); + auto functorId = m_method.getLambdaById(detail::TypeId>::get()); if (functorId) [[likely]] { const auto& erased = functorId->m_lambda->m_erasure; diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_function.h b/ReflectionTemplateLib/rtl/dispatch/functor_function.h index 0ce1b59c..60fbb3d1 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor_function.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor_function.h @@ -33,7 +33,7 @@ namespace rtl::dispatch function_ptr(functor_t fptr) :m_functor(fptr) { m_returnId = detail::TypeId::get(); - m_signatureId = detail::TypeId...>>::get(); + m_signatureId = detail::TypeId>::get(); m_returnStr = detail::TypeId::toString(); m_signatureStr = detail::TypeId::toString(); diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_method.h b/ReflectionTemplateLib/rtl/dispatch/functor_method.h index 479e3ba5..07d44384 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor_method.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor_method.h @@ -37,7 +37,7 @@ namespace rtl::dispatch m_qualifier = detail::methodQ::NonConst; m_recordId = detail::TypeId::get(); m_returnId = detail::TypeId::get(); - m_signatureId = detail::TypeId...>>::get(); + m_signatureId = detail::TypeId>::get(); m_returnStr = detail::TypeId::toString(); m_recordStr = detail::TypeId::toString(); diff --git a/ReflectionTemplateLib/rtl/dispatch/functor_method_const.h b/ReflectionTemplateLib/rtl/dispatch/functor_method_const.h index 002c7794..662714e9 100644 --- a/ReflectionTemplateLib/rtl/dispatch/functor_method_const.h +++ b/ReflectionTemplateLib/rtl/dispatch/functor_method_const.h @@ -37,7 +37,7 @@ namespace rtl::dispatch m_qualifier = detail::methodQ::Const; m_recordId = detail::TypeId::get(); m_returnId = detail::TypeId::get(); - m_signatureId = detail::TypeId...>>::get(); + m_signatureId = detail::TypeId>::get(); m_returnStr = detail::TypeId::toString(); m_recordStr = detail::TypeId::toString(); diff --git a/ReflectionTemplateLib/rtl/rtl_traits.h b/ReflectionTemplateLib/rtl/rtl_traits.h index e1a53809..46b92387 100644 --- a/ReflectionTemplateLib/rtl/rtl_traits.h +++ b/ReflectionTemplateLib/rtl/rtl_traits.h @@ -142,4 +142,14 @@ namespace rtl return !(std::is_const_v || std::is_pointer_v || std::is_reference_v); } } +} + + +namespace rtl::traits +{ + template + using sign_t = std::tuple; + + template + using fwd_sign_t = std::tuple...>; } \ No newline at end of file