summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSven Gothel <[email protected]>2020-05-03 20:26:26 +0200
committerSven Gothel <[email protected]>2020-05-03 20:26:26 +0200
commit2a59dbf5a8a14282d1a6b103bd0f834ecb0fa674 (patch)
treec8ff5b2e89b2fa3ea2fb77c619fceb2c1edebb5b
parent0423ea822a9cf33f65e131e29a15ec6911b45336 (diff)
FunctionDef: Add CaptureInvocationFunc supporting lambdas w/ an explicit capture instance
Commit efa490bc3f55b1af072b5159d075afece018991f introduced StdInvocationFunc, which utilized std:function for capturing lambdas. Since it requires to pass a unique key for equality operation, it is rather a poor workaround for capturing lambdas. CaptureInvocationFunc allows one explicit capture data type to be stored, which will be implicitly passed to the custom function @ invoke. The bindCaptureFunc(..) allows to set dataIsIdentity=false (defaults to true), i.e. ignore the capturing data to be compared in the equality operation. CaptureInvocationFunc allows producing FunctionDef using lambdas on-the-fly, w/o specifying an explicit unique key and dropping the usage of a more complex std::function instance.
-rw-r--r--api/direct_bt/FunctionDef.hpp92
-rw-r--r--test/direct_bt/CMakeLists.txt7
-rw-r--r--test/direct_bt/test_basictypes01.cpp109
-rw-r--r--test/direct_bt/test_functiondef01.cpp222
4 files changed, 306 insertions, 124 deletions
diff --git a/api/direct_bt/FunctionDef.hpp b/api/direct_bt/FunctionDef.hpp
index e883ddb9..ce2ef0e3 100644
--- a/api/direct_bt/FunctionDef.hpp
+++ b/api/direct_bt/FunctionDef.hpp
@@ -100,6 +100,32 @@ namespace direct_bt {
};
template<typename R, typename C, typename... A>
+ class NullInvocationFunc : public InvocationFunc<R, A...> {
+ public:
+ NullInvocationFunc() { }
+
+ int getType() const override { return 0; }
+
+ R invoke(A... args) const override {
+ return (R)0;
+ }
+
+ bool operator==(const InvocationFunc<R, A...>& rhs) const override
+ {
+ return getType() == rhs.getType();
+ }
+
+ bool operator!=(const InvocationFunc<R, A...>& rhs) const override
+ {
+ return !( *this == rhs );
+ }
+
+ std::string toString() const override {
+ return "NIL";
+ }
+ };
+
+ template<typename R, typename C, typename... A>
class ClassInvocationFunc : public InvocationFunc<R, A...> {
private:
C* base;
@@ -127,11 +153,7 @@ namespace direct_bt {
bool operator!=(const InvocationFunc<R, A...>& rhs) const override
{
- if( getType() != rhs.getType() ) {
- return true;
- }
- const ClassInvocationFunc<R, C, A...> * prhs = static_cast<const ClassInvocationFunc<R, C, A...>*>(&rhs);
- return base != prhs->base || member != prhs->member;
+ return !( *this == rhs );
}
std::string toString() const override {
@@ -167,11 +189,45 @@ namespace direct_bt {
bool operator!=(const InvocationFunc<R, A...>& rhs) const override
{
+ return !( *this == rhs );
+ }
+
+ std::string toString() const override {
+ // hack to convert function pointer to void *: '*((void**)&function)'
+ return aptrHexString( *((void**)&function) );
+ }
+ };
+
+ template<typename R, typename I, typename... A>
+ class CaptureInvocationFunc : public InvocationFunc<R, A...> {
+ private:
+ I data;
+ R(*function)(I, A...);
+ bool dataIsIdentity;
+
+ public:
+ CaptureInvocationFunc(I _data, R(*_function)(I, A...), bool dataIsIdentity)
+ : data(_data), function(_function), dataIsIdentity(dataIsIdentity) {
+ }
+
+ int getType() const override { return 3; }
+
+ R invoke(A... args) const override {
+ return (*function)(data, args...);
+ }
+
+ bool operator==(const InvocationFunc<R, A...>& rhs) const override
+ {
if( getType() != rhs.getType() ) {
- return true;
+ return false;
}
- const PlainInvocationFunc<R, A...> * prhs = static_cast<const PlainInvocationFunc<R, A...>*>(&rhs);
- return function != prhs->function;
+ const CaptureInvocationFunc<R, I, A...> * prhs = static_cast<const CaptureInvocationFunc<R, I, A...>*>(&rhs);
+ return dataIsIdentity == prhs->dataIsIdentity && function == prhs->function && ( !dataIsIdentity || data == prhs->data );
+ }
+
+ bool operator!=(const InvocationFunc<R, A...>& rhs) const override
+ {
+ return !( *this == rhs );
}
std::string toString() const override {
@@ -194,7 +250,7 @@ namespace direct_bt {
: id(_id), function() {
}
- int getType() const override { return 3; }
+ int getType() const override { return 10; }
R invoke(A... args) const override {
return function(args...);
@@ -211,11 +267,7 @@ namespace direct_bt {
bool operator!=(const InvocationFunc<R, A...>& rhs) const override
{
- if( getType() != rhs.getType() ) {
- return true;
- }
- const StdInvocationFunc<R, A...> * prhs = static_cast<const StdInvocationFunc<R, A...>*>(&rhs);
- return id != prhs->id;
+ return !( *this == rhs );
}
std::string toString() const override {
@@ -229,6 +281,10 @@ namespace direct_bt {
std::shared_ptr<InvocationFunc<R, A...>> func;
public:
+ FunctionDef()
+ : func(std::shared_ptr<InvocationFunc<R, A...>>( new NullInvocationFunc<R, A...>() ))
+ {};
+
FunctionDef(std::shared_ptr<InvocationFunc<R, A...>> _func)
: func(_func) { }
@@ -268,6 +324,14 @@ namespace direct_bt {
);
}
+ template<typename R, typename I, typename... A>
+ inline FunctionDef<R, A...>
+ bindCaptureFunc(I data, R(*func)(I, A...), bool dataIsIdentity=true) {
+ return FunctionDef<R, A...>(
+ std::shared_ptr<InvocationFunc<R, A...>>( new CaptureInvocationFunc<R, I, A...>(data, func, dataIsIdentity) )
+ );
+ }
+
template<typename R, typename... A>
inline FunctionDef<R, A...>
bindStdFunc(uint64_t id, std::function<R(A...)> func) {
diff --git a/test/direct_bt/CMakeLists.txt b/test/direct_bt/CMakeLists.txt
index 0aad6245..8e294b08 100644
--- a/test/direct_bt/CMakeLists.txt
+++ b/test/direct_bt/CMakeLists.txt
@@ -3,6 +3,7 @@ include_directories(
${PROJECT_SOURCE_DIR}/api
)
+add_executable (test_functiondef01 test_functiondef01.cpp)
add_executable (test_uuid test_uuid.cpp)
add_executable (test_basictypes01 test_basictypes01.cpp)
add_executable (test_attpdu01 test_attpdu01.cpp)
@@ -11,14 +12,18 @@ add_executable (test_lfringbuffer11 test_lfringbuffer11.cpp)
set_target_properties(list_mfg
PROPERTIES
- CXX_STANDARD 11)
+ CXX_STANDARD 11
+ COMPILE_FLAGS "-Wall -Wextra -Werror"
+)
+target_link_libraries (test_functiondef01 direct_bt)
target_link_libraries (test_basictypes01 direct_bt)
target_link_libraries (test_uuid direct_bt)
target_link_libraries (test_attpdu01 direct_bt)
target_link_libraries (test_lfringbuffer01 direct_bt)
target_link_libraries (test_lfringbuffer11 direct_bt)
+add_test (NAME functiondef01 COMMAND test_functiondef01)
add_test (NAME basictypes01 COMMAND test_basictypes01)
add_test (NAME uuid COMMAND test_uuid)
add_test (NAME attpdu01 COMMAND test_attpdu01)
diff --git a/test/direct_bt/test_basictypes01.cpp b/test/direct_bt/test_basictypes01.cpp
index e40370c4..e692697a 100644
--- a/test/direct_bt/test_basictypes01.cpp
+++ b/test/direct_bt/test_basictypes01.cpp
@@ -7,7 +7,6 @@
#include <direct_bt/BasicTypes.hpp>
#include <direct_bt/BTAddress.hpp>
-#include <direct_bt/FunctionDef.hpp>
using namespace direct_bt;
@@ -39,116 +38,8 @@ class Cppunit_tests : public Cppunit {
CHECKTM(msg, str == expStr);
}
- int func2a_member(int i) {
- int res = i+100;
- return res;;
- }
- int func2b_member(int i) {
- int res = i+1000;
- return res;;
- }
- static int Func3a_static(int i) {
- int res = i+100;
- return res;;
- }
- static int Func3b_static(int i) {
- int res = i+1000;
- return res;;
- }
-
- // template<typename R, typename... A>
- typedef FunctionDef<int, int> MyClassFunction;
-
- void test_FunctionPointer00(std::string msg, bool expEqual, int value, int expRes, MyClassFunction & f1, MyClassFunction &f2) {
- // test std::function identity
- PRINTM(msg+": FunctionPointer00 Fun f1p == f2p : " + std::to_string( f1 == f2 ) + ", f1p: " + f1.toString() + ", f2 "+f2.toString() );
- int f1r = f1.invoke(value);
- int f2r = f2.invoke(value);
- PRINTM(msg+": FunctionPointer00 Res f1r == f2r : " + std::to_string( f1r == f2r ) + ", f1r: " + std::to_string( f1r ) + ", f2r "+std::to_string( f2r ) );
- if( expEqual ) {
- CHECKM(msg, f1r, expRes);
- CHECKM(msg, f2r, expRes);
- CHECKTM(msg, f1 == f2);
- } else {
- CHECKTM(msg, f1 != f2);
- }
- }
- void test_FunctionPointer01(std::string msg, bool expEqual, MyClassFunction & f1, MyClassFunction &f2) {
- // test std::function identity
- PRINTM(msg+": FunctionPointer00 Fun f1p == f2p : " + std::to_string( f1 == f2 ) + ", f1p: " + f1.toString() + ", f2 "+f2.toString() );
- if( expEqual ) {
- CHECKTM(msg, f1 == f2);
- } else {
- CHECKTM(msg, f1 != f2);
- }
- }
-
public:
void single_test() override {
-
- {
- // FunctionDef(Cppunit_tests &base, Func1Type func)
- MyClassFunction f2a_1 = bindMemberFunc<int, Cppunit_tests, int>(this, &Cppunit_tests::func2a_member);
- MyClassFunction f2a_2 = bindMemberFunc(this, &Cppunit_tests::func2a_member);
- test_FunctionPointer00("FuncPtr2a_member_11", true, 1, 101, f2a_1, f2a_1);
- test_FunctionPointer00("FuncPtr2a_member_12", true, 1, 101, f2a_1, f2a_2);
-
- MyClassFunction f2b_1 = bindMemberFunc(this, &Cppunit_tests::func2b_member);
- MyClassFunction f2b_2 = bindMemberFunc(this, &Cppunit_tests::func2b_member);
- test_FunctionPointer00("FuncPtr2b_member_11", true, 1, 1001, f2b_1, f2b_1);
- test_FunctionPointer00("FuncPtr2b_member_12", true, 1, 1001, f2b_1, f2b_2);
-
- test_FunctionPointer00("FuncPtr2ab_member_11", false, 1, 0, f2a_1, f2b_1);
- test_FunctionPointer00("FuncPtr2ab_member_22", false, 1, 0, f2a_2, f2b_2);
- }
- {
- // FunctionDef(Func1Type func)
- MyClassFunction f3a_1 = bindPlainFunc<int, int>(&Cppunit_tests::Func3a_static);
- MyClassFunction f3a_2 = bindPlainFunc(&Cppunit_tests::Func3a_static);
- test_FunctionPointer00("FuncPtr3a_static_11", true, 1, 101, f3a_1, f3a_1);
- test_FunctionPointer00("FuncPtr3a_static_12", true, 1, 101, f3a_1, f3a_2);
-
- MyClassFunction f3b_1 = bindPlainFunc(&Cppunit_tests::Func3b_static);
- MyClassFunction f3b_2 = bindPlainFunc(&Func3b_static);
- test_FunctionPointer00("FuncPtr3b_static_11", true, 1, 1001, f3b_1, f3b_1);
- test_FunctionPointer00("FuncPtr3b_static_12", true, 1, 1001, f3b_1, f3b_2);
-
- test_FunctionPointer00("FuncPtr3ab_static_11", false, 1, 0, f3a_1, f3b_1);
- test_FunctionPointer00("FuncPtr3ab_static_22", false, 1, 0, f3a_2, f3b_2);
- }
- {
- // FunctionDef(Func1Type func) <int, int>
- std::function<int(int i)> func4a_stdlambda = [](int i)->int {
- int res = i+100;
- return res;;
- };
- std::function<int(int i)> func4b_stdlambda = [](int i)->int {
- int res = i+1000;
- return res;;
- };
- MyClassFunction f3a_1 = bindStdFunc<int, int>(100, func4a_stdlambda);
- MyClassFunction f3a_2 = bindStdFunc(100, func4a_stdlambda);
- test_FunctionPointer00("FuncPtr4a_stdlambda_11", true, 1, 101, f3a_1, f3a_1);
- test_FunctionPointer00("FuncPtr4a_stdlambda_12", true, 1, 101, f3a_1, f3a_2);
-
- MyClassFunction f3b_1 = bindStdFunc(200, func4b_stdlambda);
- MyClassFunction f3b_2 = bindStdFunc(200, func4b_stdlambda);
- test_FunctionPointer00("FuncPtr4b_stdlambda_11", true, 1, 1001, f3b_1, f3b_1);
- test_FunctionPointer00("FuncPtr4b_stdlambda_12", true, 1, 1001, f3b_1, f3b_2);
-
- test_FunctionPointer00("FuncPtr4ab_stdlambda_11", false, 1, 0, f3a_1, f3b_1);
- test_FunctionPointer00("FuncPtr4ab_stdlambda_22", false, 1, 0, f3a_2, f3b_2);
-
- MyClassFunction f3a_0 = bindStdFunc<int, int>(100);
- MyClassFunction f3b_0 = bindStdFunc<int, int>(200);
- test_FunctionPointer01("FuncPtr4a_stdlambda_01", true, f3a_0, f3a_1);
- test_FunctionPointer01("FuncPtr4a_stdlambda_02", true, f3a_0, f3a_2);
- test_FunctionPointer01("FuncPtr4b_stdlambda_01", true, f3b_0, f3b_1);
- test_FunctionPointer01("FuncPtr4b_stdlambda_02", true, f3b_0, f3b_2);
- test_FunctionPointer01("FuncPtr4ab_stdlambda_00", false, f3a_0, f3b_0);
- test_FunctionPointer01("FuncPtr4ab_stdlambda_01", false, f3a_0, f3b_1);
- test_FunctionPointer01("FuncPtr4ab_stdlambda_10", false, f3a_1, f3b_0);
- }
{
test_int32_t("INT32_MIN", INT32_MIN, 14, "-2,147,483,648");
test_int32_t("int32_t -thousand", -1000, 6, "-1,000");
diff --git a/test/direct_bt/test_functiondef01.cpp b/test/direct_bt/test_functiondef01.cpp
new file mode 100644
index 00000000..22948610
--- /dev/null
+++ b/test/direct_bt/test_functiondef01.cpp
@@ -0,0 +1,222 @@
+#include <iostream>
+#include <cassert>
+#include <cinttypes>
+#include <cstring>
+
+#include <cppunit.h>
+
+#include <direct_bt/FunctionDef.hpp>
+
+using namespace direct_bt;
+
+// Test examples.
+class Cppunit_tests : public Cppunit {
+ private:
+
+ int func2a_member(int i) {
+ int res = i+100;
+ return res;;
+ }
+ int func2b_member(int i) {
+ int res = i+1000;
+ return res;;
+ }
+ static int Func3a_static(int i) {
+ int res = i+100;
+ return res;;
+ }
+ static int Func3b_static(int i) {
+ int res = i+1000;
+ return res;;
+ }
+
+ // template<typename R, typename... A>
+ typedef FunctionDef<int, int> MyClassFunction;
+
+ struct IntOffset {
+ int value;
+ IntOffset(int v) : value(v) {}
+ };
+
+ void test_FunctionPointer00(std::string msg, bool expEqual, int value, int expRes, MyClassFunction & f1, MyClassFunction &f2) {
+ // test std::function identity
+ PRINTM(msg+": FunctionPointer00 Fun f1p == f2p : " + std::to_string( f1 == f2 ) + ", f1p: " + f1.toString() + ", f2 "+f2.toString() );
+ int f1r = f1.invoke(value);
+ int f2r = f2.invoke(value);
+ PRINTM(msg+": FunctionPointer00 Res f1r == f2r : " + std::to_string( f1r == f2r ) + ", f1r: " + std::to_string( f1r ) + ", f2r "+std::to_string( f2r ) );
+ if( expEqual ) {
+ CHECKM(msg, f1r, expRes);
+ CHECKM(msg, f2r, expRes);
+ CHECKTM(msg, f1 == f2);
+ } else {
+ CHECKTM(msg, f1 != f2);
+ }
+ }
+ void test_FunctionPointer01(std::string msg, bool expEqual, MyClassFunction & f1, MyClassFunction &f2) {
+ // test std::function identity
+ PRINTM(msg+": FunctionPointer00 Fun f1p == f2p : " + std::to_string( f1 == f2 ) + ", f1p: " + f1.toString() + ", f2 "+f2.toString() );
+ if( expEqual ) {
+ CHECKTM(msg, f1 == f2);
+ } else {
+ CHECKTM(msg, f1 != f2);
+ }
+ }
+
+ public:
+ void single_test() override {
+
+ {
+ // FunctionDef(Cppunit_tests &base, Func1Type func)
+ MyClassFunction f2a_1 = bindMemberFunc<int, Cppunit_tests, int>(this, &Cppunit_tests::func2a_member);
+ MyClassFunction f2a_2 = bindMemberFunc(this, &Cppunit_tests::func2a_member);
+ test_FunctionPointer00("FuncPtr2a_member_11", true, 1, 101, f2a_1, f2a_1);
+ test_FunctionPointer00("FuncPtr2a_member_12", true, 1, 101, f2a_1, f2a_2);
+
+ MyClassFunction f2b_1 = bindMemberFunc(this, &Cppunit_tests::func2b_member);
+ MyClassFunction f2b_2 = bindMemberFunc(this, &Cppunit_tests::func2b_member);
+ test_FunctionPointer00("FuncPtr2b_member_11", true, 1, 1001, f2b_1, f2b_1);
+ test_FunctionPointer00("FuncPtr2b_member_12", true, 1, 1001, f2b_1, f2b_2);
+
+ test_FunctionPointer00("FuncPtr2ab_member_11", false, 1, 0, f2a_1, f2b_1);
+ test_FunctionPointer00("FuncPtr2ab_member_22", false, 1, 0, f2a_2, f2b_2);
+ }
+ {
+ // FunctionDef(Func1Type func)
+ MyClassFunction f3a_1 = bindPlainFunc<int, int>(&Cppunit_tests::Func3a_static);
+ MyClassFunction f3a_2 = bindPlainFunc(&Cppunit_tests::Func3a_static);
+ test_FunctionPointer00("FuncPtr3a_static_11", true, 1, 101, f3a_1, f3a_1);
+ test_FunctionPointer00("FuncPtr3a_static_12", true, 1, 101, f3a_1, f3a_2);
+
+ MyClassFunction f3b_1 = bindPlainFunc(&Cppunit_tests::Func3b_static);
+ MyClassFunction f3b_2 = bindPlainFunc(&Func3b_static);
+ test_FunctionPointer00("FuncPtr3b_static_11", true, 1, 1001, f3b_1, f3b_1);
+ test_FunctionPointer00("FuncPtr3b_static_12", true, 1, 1001, f3b_1, f3b_2);
+
+ test_FunctionPointer00("FuncPtr3ab_static_11", false, 1, 0, f3a_1, f3b_1);
+ test_FunctionPointer00("FuncPtr3ab_static_22", false, 1, 0, f3a_2, f3b_2);
+ }
+ {
+ // FunctionDef(Func1Type func) <int, int>
+ std::function<int(int i)> func4a_stdlambda = [](int i)->int {
+ int res = i+100;
+ return res;;
+ };
+ std::function<int(int i)> func4b_stdlambda = [](int i)->int {
+ int res = i+1000;
+ return res;;
+ };
+ MyClassFunction f4a_1 = bindStdFunc<int, int>(100, func4a_stdlambda);
+ MyClassFunction f4a_2 = bindStdFunc(100, func4a_stdlambda);
+ test_FunctionPointer00("FuncPtr4a_stdlambda_11", true, 1, 101, f4a_1, f4a_1);
+ test_FunctionPointer00("FuncPtr4a_stdlambda_12", true, 1, 101, f4a_1, f4a_2);
+
+ MyClassFunction f4b_1 = bindStdFunc(200, func4b_stdlambda);
+ MyClassFunction f4b_2 = bindStdFunc(200, func4b_stdlambda);
+ test_FunctionPointer00("FuncPtr4b_stdlambda_11", true, 1, 1001, f4b_1, f4b_1);
+ test_FunctionPointer00("FuncPtr4b_stdlambda_12", true, 1, 1001, f4b_1, f4b_2);
+
+ test_FunctionPointer00("FuncPtr4ab_stdlambda_11", false, 1, 0, f4a_1, f4b_1);
+ test_FunctionPointer00("FuncPtr4ab_stdlambda_22", false, 1, 0, f4a_2, f4b_2);
+
+ MyClassFunction f4a_0 = bindStdFunc<int, int>(100);
+ MyClassFunction f4b_0 = bindStdFunc<int, int>(200);
+ test_FunctionPointer01("FuncPtr4a_stdlambda_01", true, f4a_0, f4a_1);
+ test_FunctionPointer01("FuncPtr4a_stdlambda_02", true, f4a_0, f4a_2);
+ test_FunctionPointer01("FuncPtr4b_stdlambda_01", true, f4b_0, f4b_1);
+ test_FunctionPointer01("FuncPtr4b_stdlambda_02", true, f4b_0, f4b_2);
+ test_FunctionPointer01("FuncPtr4ab_stdlambda_00", false, f4a_0, f4b_0);
+ test_FunctionPointer01("FuncPtr4ab_stdlambda_01", false, f4a_0, f4b_1);
+ test_FunctionPointer01("FuncPtr4ab_stdlambda_10", false, f4a_1, f4b_0);
+ }
+ {
+ // bindCaptureFunc(I& data, R(*func)(I&, A...))
+ // FunctionDef(Func1Type func) <int, int>
+ int offset100 = 100;
+ int offset1000 = 1000;
+
+ int(*func5a_capture)(int, int) = [](int offset, int i)->int {
+ int res = i+10000+offset;
+ return res;
+ };
+ int(*func5b_capture)(int, int) = [](int offset, int i)->int {
+ int res = i+100000+offset;
+ return res;
+ };
+
+#if 0
+ MyClassFunction f5a_o100_0 = bindCaptureFunc<int, int, int>(offset100,
+ [](int& offset, int i)->int {
+ int res = i+10000+offset;
+ return res;;
+ } );
+ test_FunctionPointer01("FuncPtr5a_o100_capture_00", true, f5a_o100_0, f5a_o100_0);
+#endif
+ MyClassFunction f5a_o100_1 = bindCaptureFunc<int, int, int>(offset100, func5a_capture);
+ MyClassFunction f5a_o100_2 = bindCaptureFunc(offset100, func5a_capture);
+ test_FunctionPointer01("FuncPtr5a_o100_capture_12", true, f5a_o100_1, f5a_o100_2);
+ test_FunctionPointer00("FuncPtr5a_o100_capture_11", true, 1, 10101, f5a_o100_1, f5a_o100_1);
+ test_FunctionPointer00("FuncPtr5a_o100_capture_12", true, 1, 10101, f5a_o100_1, f5a_o100_2);
+ // test_FunctionPointer01("FuncPtr5a_o100_capture_01", false, f5a_o100_0, f5a_o100_1);
+ MyClassFunction f5a_o1000_1 = bindCaptureFunc(offset1000, func5a_capture);
+ MyClassFunction f5a_o1000_2 = bindCaptureFunc(offset1000, func5a_capture);
+ test_FunctionPointer01("FuncPtr5a_o1000_capture_12", true, f5a_o1000_1, f5a_o1000_2);
+ test_FunctionPointer01("FuncPtr5a_o100_o1000_capture_11", false, f5a_o100_1, f5a_o1000_1);
+
+ MyClassFunction f5b_o100_1 = bindCaptureFunc(offset100, func5b_capture);
+ MyClassFunction f5b_o100_2 = bindCaptureFunc(offset100, func5b_capture);
+ test_FunctionPointer00("FuncPtr5b_o100_capture_11", true, 1, 100101, f5b_o100_1, f5b_o100_1);
+ test_FunctionPointer00("FuncPtr5b_o100_capture_12", true, 1, 100101, f5b_o100_1, f5b_o100_2);
+
+ test_FunctionPointer00("FuncPtr5ab_o100_capture_11", false, 1, 0, f5a_o100_1, f5b_o100_1);
+ test_FunctionPointer00("FuncPtr5ab_o100_capture_22", false, 1, 0, f5a_o100_2, f5b_o100_2);
+ }
+ {
+ // bindCaptureFunc(I& data, R(*func)(I&, A...))
+ // FunctionDef(Func1Type func) <int, int>
+ std::shared_ptr<IntOffset> offset100(new IntOffset(100));
+ std::shared_ptr<IntOffset> offset1000(new IntOffset(1000));
+
+ int(*func5a_capture)(std::shared_ptr<IntOffset>, int) = [](std::shared_ptr<IntOffset> sharedOffset, int i)->int {
+ int res = i+10000+sharedOffset->value;
+ return res;
+ };
+ int(*func5b_capture)(std::shared_ptr<IntOffset>, int) = [](std::shared_ptr<IntOffset> sharedOffset, int i)->int {
+ int res = i+100000+sharedOffset->value;
+ return res;
+ };
+
+#if 0
+ MyClassFunction f5a_o100_0 = bindCaptureFunc<int, std::shared_ptr<IntOffset>, int>(offset100,
+ [](std::shared_ptr<IntOffset> sharedOffset, int i)->int {
+ int res = i+10000+sharedOffset->value;
+ return res;;
+ } );
+ test_FunctionPointer01("FuncPtr5a_o100_capture_00", true, f5a_o100_0, f5a_o100_0);
+#endif
+ MyClassFunction f5a_o100_1 = bindCaptureFunc<int, std::shared_ptr<IntOffset>, int>(offset100, func5a_capture);
+ MyClassFunction f5a_o100_2 = bindCaptureFunc(offset100, func5a_capture);
+ test_FunctionPointer01("FuncPtr5a_o100_capture_12", true, f5a_o100_1, f5a_o100_2);
+ test_FunctionPointer00("FuncPtr5a_o100_capture_11", true, 1, 10101, f5a_o100_1, f5a_o100_1);
+ test_FunctionPointer00("FuncPtr5a_o100_capture_12", true, 1, 10101, f5a_o100_1, f5a_o100_2);
+ // test_FunctionPointer01("FuncPtr5a_o100_capture_01", false, f5a_o100_0, f5a_o100_1);
+ MyClassFunction f5a_o1000_1 = bindCaptureFunc(offset1000, func5a_capture);
+ MyClassFunction f5a_o1000_2 = bindCaptureFunc(offset1000, func5a_capture);
+ test_FunctionPointer01("FuncPtr5a_o1000_capture_12", true, f5a_o1000_1, f5a_o1000_2);
+ test_FunctionPointer01("FuncPtr5a_o100_o1000_capture_11", false, f5a_o100_1, f5a_o1000_1);
+
+ MyClassFunction f5b_o100_1 = bindCaptureFunc(offset100, func5b_capture);
+ MyClassFunction f5b_o100_2 = bindCaptureFunc(offset100, func5b_capture);
+ test_FunctionPointer00("FuncPtr5b_o100_capture_11", true, 1, 100101, f5b_o100_1, f5b_o100_1);
+ test_FunctionPointer00("FuncPtr5b_o100_capture_12", true, 1, 100101, f5b_o100_1, f5b_o100_2);
+
+ test_FunctionPointer00("FuncPtr5ab_o100_capture_11", false, 1, 0, f5a_o100_1, f5b_o100_1);
+ test_FunctionPointer00("FuncPtr5ab_o100_capture_22", false, 1, 0, f5a_o100_2, f5b_o100_2);
+ }
+ }
+};
+
+int main(int argc, char *argv[]) {
+ Cppunit_tests test1;
+ return test1.run();
+}
+