@@ -191,17 +191,6 @@ struct parameter_traits {
191191 }
192192};
193193
194- template <typename T, class Registry >
195- struct parameter_traits <virtual_<T>, Registry> : virtual_traits<T, Registry> {};
196-
197- template <class Class , class Registry >
198- struct parameter_traits <virtual_ptr<Class, Registry>, Registry>
199- : virtual_traits<virtual_ptr<Class, Registry>, Registry> {};
200-
201- template <class Class , class Registry >
202- struct parameter_traits <const virtual_ptr<Class, Registry>&, Registry>
203- : virtual_traits<const virtual_ptr<Class, Registry>&, Registry> {};
204-
205194} // namespace detail
206195
207196// =============================================================================
@@ -281,22 +270,29 @@ struct use_classes {
281270template <class Registry , typename Argype>
282271inline auto final_virtual_ptr (Argype&& obj);
283272
273+ template <
274+ class Class , class Registry = BOOST_OPENMETHOD_DEFAULT_REGISTRY ,
275+ typename = void >
276+ class virtual_ptr ;
277+
284278namespace detail {
285279
286280template <class Class , class Registry >
287- struct is_virtual <virtual_ptr<Class, Registry>> : std::true_type {};
281+ struct is_virtual <virtual_ptr<Class, Registry, void >> : std::true_type {};
288282
289283template <class Class , class Registry >
290- struct is_virtual <const virtual_ptr<Class, Registry>&> : std::true_type {};
284+ struct is_virtual <const virtual_ptr<Class, Registry, void >&> : std::true_type {
285+ };
291286
292287template <typename >
293288struct is_virtual_ptr_aux : std::false_type {};
294289
295290template <class Class , class Registry >
296- struct is_virtual_ptr_aux <virtual_ptr<Class, Registry>> : std::true_type {};
291+ struct is_virtual_ptr_aux <virtual_ptr<Class, Registry, void >> : std::true_type {
292+ };
297293
298294template <class Class , class Registry >
299- struct is_virtual_ptr_aux <const virtual_ptr<Class, Registry>&>
295+ struct is_virtual_ptr_aux <const virtual_ptr<Class, Registry, void >&>
300296 : std::true_type {};
301297
302298template <typename T>
@@ -342,8 +338,11 @@ inline vptr_type null_vptr = nullptr;
342338
343339} // namespace detail
344340
345- template <class Class , class Registry , typename = void >
346- class virtual_ptr_impl {
341+ template <class Class , class Registry , typename >
342+ class virtual_ptr {
343+ template <class , class , typename >
344+ friend class virtual_ptr ;
345+
347346 public:
348347 static constexpr bool use_indirect_vptrs =
349348 Registry::template has_policy<policies::indirect_vptr>;
@@ -357,9 +356,9 @@ class virtual_ptr_impl {
357356 using element_type = Class;
358357 static constexpr bool is_smart_ptr = false ;
359358
360- virtual_ptr_impl () = default ;
359+ virtual_ptr () = default ;
361360
362- explicit virtual_ptr_impl (std::nullptr_t )
361+ explicit virtual_ptr (std::nullptr_t )
363362 : vp(detail::box_vptr<use_indirect_vptrs>(detail::null_vptr)),
364363 obj(nullptr ) {
365364 }
@@ -369,7 +368,7 @@ class virtual_ptr_impl {
369368 typename = std::enable_if_t <
370369 std::is_constructible_v<Class*, Other*> &&
371370 is_polymorphic<Registry, Class>>>
372- virtual_ptr_impl (Other& other)
371+ virtual_ptr (Other& other)
373372 : vp(detail::box_vptr<use_indirect_vptrs>(
374373 detail::acquire_vptr<Registry>(other))),
375374 obj (&other) {
@@ -382,7 +381,7 @@ class virtual_ptr_impl {
382381 Class*,
383382 decltype (std::declval<virtual_ptr<Other, Registry>>().get())> &&
384383 is_polymorphic<Registry, Class>>>
385- virtual_ptr_impl (Other* other)
384+ virtual_ptr (Other* other)
386385 : vp(detail::box_vptr<use_indirect_vptrs>(
387386 detail::acquire_vptr<Registry>(*other))),
388387 obj(other) {
@@ -393,7 +392,7 @@ class virtual_ptr_impl {
393392 typename = std::enable_if_t <std::is_constructible_v<
394393 Class*,
395394 decltype (std::declval<virtual_ptr<Other, Registry>>().get())>>>
396- virtual_ptr_impl (const virtual_ptr<Other, Registry>& other)
395+ virtual_ptr (const virtual_ptr<Other, Registry>& other)
397396 : vp(other.vp), obj(other.get()) {
398397 }
399398
@@ -402,30 +401,30 @@ class virtual_ptr_impl {
402401 typename = std::enable_if_t <std::is_constructible_v<
403402 Class*,
404403 decltype (std::declval<virtual_ptr<Other, Registry>>().get())>>>
405- virtual_ptr_impl(virtual_ptr_impl <Other, Registry>& other)
404+ virtual_ptr(virtual_ptr <Other, Registry>& other)
406405 : vp(other.vp), obj(other.get()) {
407406 // Why is this needed? Consider this conversion conversion from
408407 // smart to dumb pointer:
409408 // virtual_ptr<std::shared_ptr<const Node>> p = ...;
410409 // virtual_ptr<const Node> q = p;
411410 // Since 'p' is not const, in the absence of this ctor,
412- // virtual_ptr_impl (Other&) would be preferred to
413- // virtual_ptr_impl (const virtual_ptr<Other, Registry>& other), and
411+ // virtual_ptr (Other&) would be preferred to
412+ // virtual_ptr (const virtual_ptr<Other, Registry>& other), and
414413 // that is incorrect.
415414 }
416415
417416 template <
418417 class Other ,
419418 typename = std::enable_if_t <std::is_constructible_v<Class*, Other*>>>
420- virtual_ptr_impl (Other& other, decltype (vp) vp) : vp(vp), obj(&other) {
419+ virtual_ptr (Other& other, decltype (vp) vp) : vp(vp), obj(&other) {
421420 }
422421
423422 template <
424423 class Other ,
425424 typename = std::enable_if_t <
426425 std::is_assignable_v<Class*, Other*> &&
427426 is_polymorphic<Registry, Class>>>
428- virtual_ptr_impl & operator =(Other& other) {
427+ virtual_ptr & operator =(Other& other) {
429428 obj = &other;
430429 vp = detail::box_vptr<use_indirect_vptrs>(
431430 detail::acquire_vptr<Registry>(other));
@@ -437,7 +436,7 @@ class virtual_ptr_impl {
437436 typename = std::enable_if_t <
438437 std::is_assignable_v<Class*, Other*> &&
439438 is_polymorphic<Registry, Class>>>
440- virtual_ptr_impl & operator =(Other* other) {
439+ virtual_ptr & operator =(Other* other) {
441440 obj = other;
442441 vp = detail::box_vptr<use_indirect_vptrs>(
443442 detail::acquire_vptr<Registry>(*other));
@@ -449,14 +448,13 @@ class virtual_ptr_impl {
449448 typename = std::enable_if_t <std::is_assignable_v<
450449 Class*,
451450 decltype (std::declval<virtual_ptr<Other, Registry>>().get())>>>
452- virtual_ptr_impl&
453- operator =(const virtual_ptr_impl<Other, Registry>& other) {
451+ virtual_ptr& operator =(const virtual_ptr<Other, Registry>& other) {
454452 obj = other.get ();
455453 vp = other.vp ;
456454 return *this ;
457455 }
458456
459- virtual_ptr_impl & operator =(std::nullptr_t ) {
457+ virtual_ptr & operator =(std::nullptr_t ) {
460458 obj = nullptr ;
461459 vp = detail::box_vptr<use_indirect_vptrs>(detail::null_vptr);
462460 return *this ;
@@ -518,50 +516,49 @@ constexpr bool same_smart_ptr =
518516 same_smart_ptr_aux<Class, Other, Registry>::value;
519517
520518template <class Class , class Registry >
521- class virtual_ptr_impl <
519+ class virtual_ptr <
522520 Class, Registry,
523521 std::void_t <
524522 typename virtual_traits<Class, Registry>::template rebind<Class>>> {
525523
524+ template <class , class , typename >
525+ friend class virtual_ptr ;
526+
527+ template <class , class >
528+ friend struct virtual_traits ;
529+
526530 public:
527531 using traits = virtual_traits<Class, Registry>;
528532 using element_type = typename Class::element_type;
529533
530534 static constexpr bool use_indirect_vptrs =
531535 Registry::template has_policy<policies::indirect_vptr>;
532536
533- template <class , class >
534- friend class virtual_ptr ;
535- template <class , class , typename >
536- friend class virtual_ptr_impl ;
537- template <class , class >
538- friend struct virtual_traits ;
539-
540537 protected:
541538 std::conditional_t <use_indirect_vptrs, const vptr_type*, vptr_type> vp;
542539 Class obj;
543540
544541 public:
545542 static constexpr bool is_smart_ptr = true ;
546543
547- virtual_ptr_impl ()
544+ virtual_ptr ()
548545 : vp(detail::box_vptr<use_indirect_vptrs>(detail::null_vptr)) {
549546 }
550547
551- explicit virtual_ptr_impl (std::nullptr_t )
548+ explicit virtual_ptr (std::nullptr_t )
552549 : vp(detail::box_vptr<use_indirect_vptrs>(detail::null_vptr)),
553550 obj(nullptr ) {
554551 }
555552
556- virtual_ptr_impl (const virtual_ptr_impl & other) = default ;
553+ virtual_ptr (const virtual_ptr & other) = default ;
557554
558555 template <
559556 class Other ,
560557 typename = std::enable_if_t <
561558 same_smart_ptr<Class, Other, Registry> &&
562559 std::is_constructible_v<Class, const Other&> &&
563560 is_polymorphic<Registry, element_type>>>
564- virtual_ptr_impl (const Other& other)
561+ virtual_ptr (const Other& other)
565562 : vp(detail::box_vptr<use_indirect_vptrs>(
566563 other ? detail::acquire_vptr<Registry>(*other)
567564 : detail::null_vptr)),
@@ -574,7 +571,7 @@ class virtual_ptr_impl<
574571 same_smart_ptr<Class, Other, Registry> &&
575572 std::is_constructible_v<Class, Other&> &&
576573 is_polymorphic<Registry, element_type>>>
577- virtual_ptr_impl (Other& other)
574+ virtual_ptr (Other& other)
578575 : vp(detail::box_vptr<use_indirect_vptrs>(
579576 other ? detail::acquire_vptr<Registry>(*other)
580577 : detail::null_vptr)),
@@ -584,7 +581,7 @@ class virtual_ptr_impl<
584581 template <
585582 class Other ,
586583 typename = std::enable_if_t <std::is_constructible_v<Class*, Other*>>>
587- virtual_ptr_impl (Other& other, decltype (vp) vp) : vp(vp), obj(&other) {
584+ virtual_ptr (Other& other, decltype (vp) vp) : vp(vp), obj(&other) {
588585 }
589586
590587 template <
@@ -593,7 +590,7 @@ class virtual_ptr_impl<
593590 same_smart_ptr<Class, Other, Registry> &&
594591 std::is_constructible_v<Class, Other&&> &&
595592 is_polymorphic<Registry, element_type>>>
596- virtual_ptr_impl (Other&& other)
593+ virtual_ptr (Other&& other)
597594 : vp(detail::box_vptr<use_indirect_vptrs>(
598595 other ? detail::acquire_vptr<Registry>(*other)
599596 : detail::null_vptr)),
@@ -605,7 +602,7 @@ class virtual_ptr_impl<
605602 typename = std::enable_if_t <
606603 same_smart_ptr<Class, Other, Registry> &&
607604 std::is_constructible_v<Class, const Other&>>>
608- virtual_ptr_impl (const virtual_ptr_impl <Other, Registry>& other)
605+ virtual_ptr (const virtual_ptr <Other, Registry>& other)
609606 : vp(other.vp), obj(other.obj) {
610607 }
611608
@@ -614,12 +611,11 @@ class virtual_ptr_impl<
614611 typename = std::enable_if_t <
615612 same_smart_ptr<Class, Other, Registry> &&
616613 std::is_constructible_v<Class, Other&>>>
617- virtual_ptr_impl (virtual_ptr_impl <Other, Registry>& other)
614+ virtual_ptr (virtual_ptr <Other, Registry>& other)
618615 : vp(other.vp), obj(other.obj) {
619616 }
620617
621- virtual_ptr_impl (virtual_ptr_impl&& other)
622- : vp(other.vp), obj(std::move(other.obj)) {
618+ virtual_ptr (virtual_ptr&& other) : vp(other.vp), obj(std::move(other.obj)) {
623619 other.vp = detail::box_vptr<use_indirect_vptrs>(detail::null_vptr);
624620 }
625621
@@ -628,17 +624,17 @@ class virtual_ptr_impl<
628624 typename = std::enable_if_t <
629625 same_smart_ptr<Class, Other, Registry> &&
630626 std::is_constructible_v<Class, Other&&>>>
631- virtual_ptr_impl (virtual_ptr_impl <Other, Registry>&& other)
627+ virtual_ptr (virtual_ptr <Other, Registry>&& other)
632628 : vp(other.vp), obj(std::move(other.obj)) {
633629 other.vp = detail::box_vptr<use_indirect_vptrs>(detail::null_vptr);
634630 }
635631
636632 template <typename Arg>
637- virtual_ptr_impl (Arg&& obj, decltype (vp) vp)
633+ virtual_ptr (Arg&& obj, decltype (vp) vp)
638634 : vp(vp), obj(std::forward<Arg>(obj)) {
639635 }
640636
641- virtual_ptr_impl & operator =(std::nullptr_t ) {
637+ virtual_ptr & operator =(std::nullptr_t ) {
642638 obj = nullptr ;
643639 vp = detail::box_vptr<use_indirect_vptrs>(detail::null_vptr);
644640 return *this ;
@@ -650,7 +646,7 @@ class virtual_ptr_impl<
650646 same_smart_ptr<Class, Other, Registry> &&
651647 std::is_assignable_v<Class, const Other&> &&
652648 is_polymorphic<Registry, element_type>>>
653- virtual_ptr_impl & operator =(const Other& other) {
649+ virtual_ptr & operator =(const Other& other) {
654650 obj = other;
655651 vp = detail::box_vptr<use_indirect_vptrs>(
656652 detail::acquire_vptr<Registry>(*other));
@@ -663,7 +659,7 @@ class virtual_ptr_impl<
663659 same_smart_ptr<Class, Other, Registry> &&
664660 std::is_assignable_v<Class, Other&&> &&
665661 is_polymorphic<Registry, element_type>>>
666- virtual_ptr_impl & operator =(Other&& other) {
662+ virtual_ptr & operator =(Other&& other) {
667663 vp = detail::box_vptr<use_indirect_vptrs>(
668664 other ? detail::acquire_vptr<Registry>(*other) : detail::null_vptr);
669665 obj = std::move (other);
@@ -675,21 +671,20 @@ class virtual_ptr_impl<
675671 typename = std::enable_if_t <
676672 same_smart_ptr<Class, Other, Registry> &&
677673 std::is_assignable_v<Class, Other&>>>
678- virtual_ptr_impl & operator =(virtual_ptr_impl <Other, Registry>& other) {
674+ virtual_ptr & operator =(virtual_ptr <Other, Registry>& other) {
679675 obj = other.obj ;
680676 vp = other.vp ;
681677 return *this ;
682678 }
683679
684- virtual_ptr_impl & operator =(const virtual_ptr_impl & other) = default ;
680+ virtual_ptr & operator =(const virtual_ptr & other) = default ;
685681
686682 template <
687683 class Other ,
688684 typename = std::enable_if_t <
689685 same_smart_ptr<Class, Other, Registry> &&
690686 std::is_assignable_v<Class, const Other&>>>
691- virtual_ptr_impl&
692- operator =(const virtual_ptr_impl<Other, Registry>& other) {
687+ virtual_ptr& operator =(const virtual_ptr<Other, Registry>& other) {
693688 obj = other.obj ;
694689 vp = other.vp ;
695690 return *this ;
@@ -700,7 +695,7 @@ class virtual_ptr_impl<
700695 typename = std::enable_if_t <
701696 same_smart_ptr<Class, Other, Registry> &&
702697 std::is_assignable_v<Class, Other&&>>>
703- virtual_ptr_impl & operator =(virtual_ptr_impl <Other, Registry>&& other) {
698+ virtual_ptr & operator =(virtual_ptr <Other, Registry>&& other) {
704699 obj = std::move (other.obj );
705700 vp = other.vp ;
706701 other.vp = detail::box_vptr<use_indirect_vptrs>(detail::null_vptr);
@@ -806,26 +801,6 @@ inline auto final_virtual_ptr(Class&& obj) {
806801 std::forward<Class>(obj));
807802}
808803
809- template <class Class , class Registry = BOOST_OPENMETHOD_DEFAULT_REGISTRY >
810- class virtual_ptr : public virtual_ptr_impl <Class, Registry> {
811- using impl = virtual_ptr_impl<Class, Registry>;
812-
813- public:
814- using virtual_ptr_impl<Class, Registry>::virtual_ptr_impl;
815- using element_type = typename impl::element_type;
816-
817- template <class , class , typename >
818- friend class virtual_ptr_impl ;
819-
820- template <
821- typename Other,
822- typename = std::enable_if_t <std::is_assignable_v<impl, Other>>>
823- virtual_ptr& operator =(Other&& other) {
824- impl::operator =(std::forward<Other>(other));
825- return *this ;
826- }
827- };
828-
829804template <class Class >
830805virtual_ptr (Class&) -> virtual_ptr<Class, BOOST_OPENMETHOD_DEFAULT_REGISTRY >;
831806
@@ -1270,6 +1245,19 @@ auto method<Name, ReturnType(Parameters...), Registry>::check_static_offset(
12701245// -----------------------------------------------------------------------------
12711246// method dispatch
12721247
1248+ namespace detail {
1249+ template <typename T, class Registry >
1250+ struct parameter_traits <virtual_<T>, Registry> : virtual_traits<T, Registry> {};
1251+
1252+ template <class Class , class Registry >
1253+ struct parameter_traits <virtual_ptr<Class, Registry, void >, Registry>
1254+ : virtual_traits<virtual_ptr<Class, Registry, void >, Registry> {};
1255+
1256+ template <class Class , class Registry >
1257+ struct parameter_traits <const virtual_ptr<Class, Registry, void >&, Registry>
1258+ : virtual_traits<const virtual_ptr<Class, Registry, void >&, Registry> {};
1259+ } // namespace detail
1260+
12731261template <
12741262 typename Name, typename ... Parameters, typename ReturnType, class Registry >
12751263BOOST_FORCEINLINE auto
0 commit comments