diff --git a/include/boost/function.hpp b/include/boost/function.hpp index 31b1f0b..462f518 100644 --- a/include/boost/function.hpp +++ b/include/boost/function.hpp @@ -459,10 +459,9 @@ namespace boost { function(const Functor& f) : base_type(f) {} #ifdef __BORLANDC__ - template - function(Functor* f) : base_type(f) {} + template function(Functor* f) : base_type(f) {} #endif // __BORLANDC__ - + function(const self_type& f) : base_type(static_cast(f)){} template diff --git a/include/boost/function/function_base.hpp b/include/boost/function/function_base.hpp index e97b394..e439f54 100644 --- a/include/boost/function/function_base.hpp +++ b/include/boost/function/function_base.hpp @@ -79,17 +79,13 @@ namespace boost { * so function requires a union of the two. */ union any_pointer { - struct container {}; - void* obj_ptr; const void* const_obj_ptr; void (*func_ptr)(); - void (container::* mem_func_ptr)(); explicit any_pointer(void* p) : obj_ptr(p) {} explicit any_pointer(const void* p) : const_obj_ptr(p) {} explicit any_pointer(void (*p)()) : func_ptr(p) {} - explicit any_pointer(void (container::*p)()) : mem_func_ptr(p) {} }; /** @@ -118,8 +114,8 @@ namespace boost { // The operation type to perform on the given functor/function pointer enum functor_manager_operation_type { - clone_functor, - destroy_functor + clone_functor_tag, + destroy_functor_tag }; // Tags used to decide between different types of functions @@ -155,26 +151,12 @@ namespace boost { manager(any_pointer function_ptr, functor_manager_operation_type op, function_ptr_tag) { - if (op == clone_functor) + if (op == clone_functor_tag) return function_ptr; else return any_pointer(static_cast(0)); } - // For member function pointers, the manager is trivial - static inline any_pointer - manager(any_pointer member_ptr, functor_manager_operation_type op, - member_ptr_tag) - { - if (op == clone_functor) - return member_ptr; - else { - typedef void (any_pointer::container::* stored_mem_func_type)(); - stored_mem_func_type p = 0; - return any_pointer(p); - } - } - // For function object pointers, we clone the pointer to each // function has its own version. static inline any_pointer @@ -194,7 +176,7 @@ namespace boost { allocator_type allocator; # endif // BOOST_NO_STD_ALLOCATOR - if (op == clone_functor) { + if (op == clone_functor_tag) { functor_type* f = static_cast(function_obj_ptr.obj_ptr); diff --git a/include/boost/function/function_template.hpp b/include/boost/function/function_template.hpp index bbe61c3..e0dae22 100644 --- a/include/boost/function/function_template.hpp +++ b/include/boost/function/function_template.hpp @@ -50,16 +50,10 @@ BOOST_JOIN(function_obj_invoker,BOOST_FUNCTION_NUM_ARGS) #define BOOST_FUNCTION_VOID_FUNCTION_OBJ_INVOKER \ BOOST_JOIN(void_function_obj_invoker,BOOST_FUNCTION_NUM_ARGS) -#define BOOST_FUNCTION_MEM_FUNCTION_INVOKER \ - BOOST_JOIN(mem_function_invoker,BOOST_FUNCTION_NUM_ARGS) -#define BOOST_FUNCTION_VOID_MEM_FUNCTION_INVOKER \ - BOOST_JOIN(void_mem_function_invoker,BOOST_FUNCTION_NUM_ARGS) #define BOOST_FUNCTION_GET_FUNCTION_INVOKER \ BOOST_JOIN(get_function_invoker,BOOST_FUNCTION_NUM_ARGS) #define BOOST_FUNCTION_GET_FUNCTION_OBJ_INVOKER \ BOOST_JOIN(get_function_obj_invoker,BOOST_FUNCTION_NUM_ARGS) -#define BOOST_FUNCTION_GET_MEM_FUNCTION_INVOKER \ - BOOST_JOIN(get_mem_function_invoker,BOOST_FUNCTION_NUM_ARGS) namespace boost { namespace detail { @@ -130,43 +124,6 @@ namespace boost { } }; -#if BOOST_FUNCTION_NUM_ARGS > 0 - template< - typename MemFunctionPtr, - typename R BOOST_FUNCTION_COMMA - BOOST_FUNCTION_TEMPLATE_PARMS - > - struct BOOST_FUNCTION_MEM_FUNCTION_INVOKER - { - static R invoke(any_pointer mem_function_ptr - BOOST_FUNCTION_COMMA - BOOST_FUNCTION_PARMS) - { - // Was a reinterpret_cast<>, but not all compilers handle it - MemFunctionPtr f = (MemFunctionPtr)(mem_function_ptr.mem_func_ptr); - return mem_fn(f)(BOOST_FUNCTION_ARGS); - } - }; - - template< - typename MemFunctionPtr, - typename R BOOST_FUNCTION_COMMA - BOOST_FUNCTION_TEMPLATE_PARMS - > - struct BOOST_FUNCTION_VOID_MEM_FUNCTION_INVOKER - { - static unusable invoke(any_pointer mem_function_ptr - BOOST_FUNCTION_COMMA - BOOST_FUNCTION_PARMS) - { - // Was a reinterpret_cast<>, but not all compilers handle it - MemFunctionPtr f = (MemFunctionPtr)(mem_function_ptr.mem_func_ptr); - mem_fn(f)(BOOST_FUNCTION_ARGS); - return unusable(); - } - }; -#endif // BOOST_FUNCTION_NUM_ARGS > 0 - template< typename FunctionPtr, typename R BOOST_FUNCTION_COMMA @@ -208,29 +165,6 @@ namespace boost { > >::type type; }; - -#if BOOST_FUNCTION_NUM_ARGS > 0 - template< - typename MemFunctionPtr, - typename R BOOST_FUNCTION_COMMA - BOOST_FUNCTION_TEMPLATE_PARMS - > - struct BOOST_FUNCTION_GET_MEM_FUNCTION_INVOKER - { - typedef typename IF<(is_void::value), - BOOST_FUNCTION_VOID_MEM_FUNCTION_INVOKER< - MemFunctionPtr, - R BOOST_FUNCTION_COMMA - BOOST_FUNCTION_TEMPLATE_ARGS - >, - BOOST_FUNCTION_MEM_FUNCTION_INVOKER< - MemFunctionPtr, - R BOOST_FUNCTION_COMMA - BOOST_FUNCTION_TEMPLATE_ARGS - > - >::type type; - }; -#endif // BOOST_FUNCTION_NUM_ARGS > 0 } // end namespace function } // end namespace detail @@ -275,6 +209,15 @@ namespace boost { this->assign_to(f); } +#ifdef __BORLANDC__ + template + BOOST_FUNCTION_FUNCTION(Functor* f) : + function_base(), Mixin(), invoker(0) + { + this->assign_to(f); + } +#endif // __BORLANDC__ + template BOOST_FUNCTION_FUNCTION(const Functor& f, const Mixin& m) : function_base(), Mixin(m), invoker(0) @@ -282,15 +225,6 @@ namespace boost { this->assign_to(f); } -#ifdef __BORLANDC__ - template - BOOST_FUNCTION_FUNCTION(Functor* f, const Mixin& m = Mixin()) : - function_base(), Mixin(m), invoker(0) - { - this->assign_to(f); - } -#endif // __BORLANDC__ - BOOST_FUNCTION_FUNCTION(const BOOST_FUNCTION_FUNCTION& f) : function_base(), Mixin(static_cast(f)), invoker(0) { @@ -382,7 +316,7 @@ namespace boost { void clear() { if (manager) - functor = manager(functor, detail::function::destroy_functor); + functor = manager(functor, detail::function::destroy_functor_tag); manager = 0; invoker = 0; @@ -394,7 +328,7 @@ namespace boost { if (!f.empty()) { invoker = f.invoker; manager = f.manager; - functor = f.manager(f.functor, detail::function::clone_functor); + functor = f.manager(f.functor, detail::function::clone_functor_tag); } } @@ -424,7 +358,7 @@ namespace boost { functor = manager(detail::function::any_pointer( reinterpret_cast(f) ), - detail::function::clone_functor); + detail::function::clone_functor_tag); } } @@ -432,28 +366,7 @@ namespace boost { template void assign_to(MemberPtr f, detail::function::member_ptr_tag) { - clear(); - - if (f) { - typedef void (detail::function::any_pointer::container:: - *stored_mem_func_type)(); - typedef - typename detail::function::BOOST_FUNCTION_GET_MEM_FUNCTION_INVOKER< - MemberPtr, - R BOOST_FUNCTION_COMMA - BOOST_FUNCTION_TEMPLATE_ARGS - >::type - invoker_type; - - invoker = &invoker_type::invoke; - manager = &detail::function::functor_manager::manage; - // Was a reinterpret_cast<>, but not all compilers handle it - functor = manager(detail::function::any_pointer( - (stored_mem_func_type)(f) - ), - detail::function::clone_functor); - } + this->assign_to(mem_fn(f)); } #endif // BOOST_FUNCTION_NUM_ARGS > 0 @@ -474,7 +387,7 @@ namespace boost { Allocator>::manage; functor = manager(detail::function::any_pointer(const_cast(&f)), - detail::function::clone_functor); + detail::function::clone_functor_tag); } } @@ -516,8 +429,6 @@ namespace boost { #undef BOOST_FUNCTION_VOID_FUNCTION_INVOKER #undef BOOST_FUNCTION_FUNCTION_OBJ_INVOKER #undef BOOST_FUNCTION_VOID_FUNCTION_OBJ_INVOKER -#undef BOOST_FUNCTION_MEM_FUNCTION_INVOKER -#undef BOOST_FUNCTION_VOID_MEM_FUNCTION_INVOKER #undef BOOST_FUNCTION_GET_FUNCTION_INVOKER #undef BOOST_FUNCTION_GET_FUNCTION_OBJ_INVOKER #undef BOOST_FUNCTION_GET_MEM_FUNCTION_INVOKER diff --git a/test/function_n_test.cpp b/test/function_n_test.cpp index 3d62bce..05f2310 100644 --- a/test/function_n_test.cpp +++ b/test/function_n_test.cpp @@ -584,6 +584,7 @@ struct X { static void test_member_functions() { + boost::function1 f1(&X::twice); X one(1);