made safe-mode iterators SCARY

This commit is contained in:
joaquintides 2021-08-11 20:59:20 +02:00
parent fee9c9d03c
commit eed24d1faa
8 changed files with 238 additions and 162 deletions

View File

@ -0,0 +1,83 @@
/* Copyright 2003-2021 Joaquin M Lopez Munoz.
* Distributed under the Boost Software License, Version 1.0.
* (See accompanying file LICENSE_1_0.txt or copy at
* http://www.boost.org/LICENSE_1_0.txt)
*
* See http://www.boost.org/libs/multi_index for library home page.
*/
#ifndef BOOST_MULTI_INDEX_DETAIL_ANY_CONTAINER_VIEW_HPP
#define BOOST_MULTI_INDEX_DETAIL_ANY_CONTAINER_VIEW_HPP
#if defined(_MSC_VER)
#pragma once
#endif
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
namespace boost{
namespace multi_index{
namespace detail{
/* TODO: WRITE */
template<typename ConstIterator>
struct any_container_view_vtable
{
ConstIterator (*begin)(const void*);
ConstIterator (*end)(const void*);
};
template<typename Container>
typename Container::const_iterator any_container_view_begin(const void* pc)
{
return static_cast<const Container*>(pc)->begin();
}
template<typename Container>
typename Container::const_iterator any_container_view_end(const void* pc)
{
return static_cast<const Container*>(pc)->end();
}
template<typename Container>
any_container_view_vtable<typename Container::const_iterator>*
any_container_view_vtable_for()
{
static any_container_view_vtable<typename Container::const_iterator> vt=
{
&any_container_view_begin<Container>,
&any_container_view_end<Container>
};
return &vt;
};
template<typename ConstIterator>
class any_container_view
{
public:
template<typename Container>
any_container_view(const Container& c):
pc(&c),
pvt(any_container_view_vtable_for<Container>())
{}
const void* container()const{return pc;}
ConstIterator begin()const{return pvt->begin(pc);}
ConstIterator end()const{return pvt->end(pc);}
private:
const void* pc;
any_container_view_vtable<ConstIterator>* pvt;
};
} /* namespace multi_index::detail */
} /* namespace multi_index */
} /* namespace boost */
#endif

View File

@ -179,7 +179,7 @@ protected:
template<typename MultiIndexContainer>
final_node_type* insert_(
const value_type& v,final_node_type*& x,MultiIndexContainer* p)
const value_type&,final_node_type*& x,MultiIndexContainer* p)
{
p->final_extract_for_transfer_(x);
return x;

View File

@ -128,13 +128,6 @@ template<
>
class ordered_index_impl:
BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS SuperMeta::type
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,public safe_mode::safe_container<
ordered_index_impl<
KeyFromValue,Compare,SuperMeta,TagList,Category,AugmentPolicy> >
#endif
{
#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)&&\
BOOST_WORKAROUND(__MWERKS__,<=0x3003)
@ -178,8 +171,7 @@ public:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef safe_mode::safe_iterator<
bidir_node_iterator<index_node_type>,
ordered_index_impl> iterator;
bidir_node_iterator<index_node_type> > iterator;
#else
typedef bidir_node_iterator<index_node_type> iterator;
#endif
@ -229,8 +221,7 @@ protected:
protected:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef safe_mode::safe_container<
ordered_index_impl> safe_super;
typedef safe_mode::safe_container<iterator> safe_container;
#endif
typedef typename call_traits<
@ -731,6 +722,11 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
super(args_list.get_tail(),al),
key(tuples::get<0>(args_list.get_head())),
comp_(tuples::get<1>(args_list.get_head()))
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,safe(*this)
#endif
{
empty_initialize();
}
@ -739,13 +735,13 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
const ordered_index_impl<
KeyFromValue,Compare,SuperMeta,TagList,Category,AugmentPolicy>& x):
super(x),
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super(),
#endif
key(x.key),
comp_(x.comp_)
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,safe(*this)
#endif
{
/* Copy ctor just takes the key and compare objects from x. The rest is
* done in a subsequent call to copy_().
@ -757,13 +753,13 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
KeyFromValue,Compare,SuperMeta,TagList,Category,AugmentPolicy>& x,
do_not_copy_elements_tag):
super(x,do_not_copy_elements_tag()),
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super(),
#endif
key(x.key),
comp_(x.comp_)
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,safe(*this)
#endif
{
empty_initialize();
}
@ -775,9 +771,9 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
iterator make_iterator(index_node_type* node)
{return iterator(node,this);}
{return iterator(node,&safe);}
const_iterator make_iterator(index_node_type* node)const
{return const_iterator(node,const_cast<ordered_index_impl*>(this));}
{return const_iterator(node,const_cast<safe_container*>(&safe));}
#else
iterator make_iterator(index_node_type* node){return iterator(node);}
const_iterator make_iterator(index_node_type* node)const
@ -904,7 +900,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
empty_initialize();
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::detach_dereferenceable_iterators();
safe.detach_dereferenceable_iterators();
#endif
}
@ -918,7 +914,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
adl_swap(comp_,x.comp_);
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::swap(x);
safe.swap(x.safe);
#endif
super::swap_(x,swap_allocators);
@ -929,7 +925,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
KeyFromValue,Compare,SuperMeta,TagList,Category,AugmentPolicy>& x)
{
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::swap(x);
safe.swap(x.safe);
#endif
super::swap_elements_(x);
@ -1531,6 +1527,10 @@ protected: /* for the benefit of AugmentPolicy::augmented_interface */
key_from_value key;
key_compare comp_;
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_container safe;
#endif
#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)&&\
BOOST_WORKAROUND(__MWERKS__,<=0x3003)
#pragma parse_mfunc_templ reset

View File

@ -18,9 +18,9 @@
/* Safe mode machinery, in the spirit of Cay Hortmann's "Safe STL"
* (http://www.horstmann.com/safestl.html).
* In this mode, containers of type Container are derived from
* safe_container<Container>, and their corresponding iterators
* are wrapped with safe_iterator. These classes provide
* In this mode, containers have to redefine their iterators as
* safe_iterator<base_iterator> and keep a tracking object member of
* type safe_container<safe_iterator<base_iterator> >. These classes provide
* an internal record of which iterators are at a given moment associated
* to a given container, and properly mark the iterators as invalid
* when the container gets destroyed.
@ -83,6 +83,11 @@
safe_mode::check_is_owner(it,cont), \
safe_mode::not_owner);
#define BOOST_MULTI_INDEX_CHECK_BELONGS_IN_SOME_INDEX(it,cont) \
BOOST_MULTI_INDEX_SAFE_MODE_ASSERT( \
safe_mode::check_belongs_in_some_index(it,cont), \
safe_mode::not_owner);
#define BOOST_MULTI_INDEX_CHECK_SAME_OWNER(it0,it1) \
BOOST_MULTI_INDEX_SAFE_MODE_ASSERT( \
safe_mode::check_same_owner(it0,it1), \
@ -117,6 +122,7 @@
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
#include <algorithm>
#include <boost/multi_index/detail/access_specifier.hpp>
#include <boost/multi_index/detail/any_container_view.hpp>
#include <boost/multi_index/detail/iter_adaptor.hpp>
#include <boost/multi_index/safe_mode_errors.hpp>
#include <boost/noncopyable.hpp>
@ -165,18 +171,29 @@ inline bool check_decrementable_iterator(const Iterator& it)
return (it.valid()&&it!=it.owner()->begin())||it.unchecked();
}
template<typename Iterator>
template<typename Iterator,typename Container>
inline bool check_is_owner(
const Iterator& it,const typename Iterator::container_type& cont)
const Iterator& it,const Container& cont)
{
return (it.valid()&&it.owner()==&cont)||it.unchecked();
return (it.valid()&&
it.owner()->container()==cont.end().owner()->container())
||it.unchecked();
}
template<typename Iterator,typename MultiIndexContainer>
inline bool check_belongs_in_some_index(
const Iterator& it,const MultiIndexContainer& cont)
{
return (it.valid()&&it.owner()->end().get_node()==cont.end().get_node())
||it.unchecked();
}
template<typename Iterator>
inline bool check_same_owner(const Iterator& it0,const Iterator& it1)
{
return (it0.valid()&&it1.valid()&&it0.owner()==it1.owner())||
it0.unchecked()||it1.unchecked();
return (it0.valid()&&it1.valid()&&
it0.owner()->container()==it1.owner()->container())
||it0.unchecked()||it1.unchecked();
}
template<typename Iterator>
@ -487,36 +504,36 @@ void safe_iterator_base::detach()
namespace safe_mode{
/* In order to enable safe mode on a container:
* - The container must derive from safe_container<container_type>,
* - The container must keep a member of type safe_container<iterator>,
* - iterators must be generated via safe_iterator, which adapts a
* preexistent unsafe iterator class.
* preexistent unsafe iterator class. safe_iterators are passed the
* address of the previous safe_container member at construction time.
*/
template<typename Container>
template<typename Iterator>
class safe_container;
template<typename Iterator,typename Container>
template<typename Iterator>
class safe_iterator:
public detail::iter_adaptor<safe_iterator<Iterator,Container>,Iterator>,
public detail::iter_adaptor<safe_iterator<Iterator>,Iterator>,
public detail::safe_iterator_base
{
typedef detail::iter_adaptor<safe_iterator,Iterator> super;
typedef detail::safe_iterator_base safe_super;
public:
typedef Container container_type;
typedef typename Iterator::reference reference;
typedef typename Iterator::difference_type difference_type;
safe_iterator(){}
explicit safe_iterator(safe_container<container_type>* cont_):
explicit safe_iterator(safe_container<safe_iterator>* cont_):
safe_super(cont_){}
template<typename T0>
safe_iterator(const T0& t0,safe_container<container_type>* cont_):
safe_iterator(const T0& t0,safe_container<safe_iterator>* cont_):
super(Iterator(t0)),safe_super(cont_){}
template<typename T0,typename T1>
safe_iterator(
const T0& t0,const T1& t1,safe_container<container_type>* cont_):
const T0& t0,const T1& t1,safe_container<safe_iterator>* cont_):
super(Iterator(t0,t1)),safe_super(cont_){}
safe_iterator(const safe_iterator& x):super(x),safe_super(x){}
@ -528,12 +545,11 @@ public:
return *this;
}
const container_type* owner()const
const safe_container<safe_iterator>* owner()const
{
return
static_cast<const container_type*>(
static_cast<const safe_container<container_type>*>(
this->safe_super::owner()));
static_cast<const safe_container<safe_iterator>*>(
this->safe_super::owner());
}
/* get_node is not to be used by the user */
@ -624,21 +640,28 @@ private:
#endif
};
template<typename Container>
template<typename Iterator>
class safe_container:public detail::safe_container_base
{
typedef detail::safe_container_base super;
detail::any_container_view<Iterator> view;
public:
template<typename Container>
safe_container(const Container& c):view(c){}
const void* container()const{return view.container();}
Iterator begin()const{return view.begin();}
Iterator end()const{return view.end();}
void detach_dereferenceable_iterators()
{
typedef typename Container::iterator iterator;
iterator end_=static_cast<Container*>(this)->end();
iterator *prev_,*next_;
Iterator end_=view.end();
Iterator *prev_,*next_;
for(
prev_=static_cast<iterator*>(&this->header);
(next_=static_cast<iterator*>(prev_->next))!=0;){
prev_=static_cast<Iterator*>(&this->header);
(next_=static_cast<Iterator*>(prev_->next))!=0;){
if(*next_!=end_){
prev_->next=next_->next;
next_->cont=0;
@ -647,7 +670,7 @@ public:
}
}
void swap(safe_container<Container>& x)
void swap(safe_container<Iterator>& x)
{
super::swap(x);
}
@ -659,9 +682,9 @@ public:
#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
namespace serialization{
template<typename Iterator,typename Container>
template<typename Iterator>
struct version<
boost::multi_index::safe_mode::safe_iterator<Iterator,Container>
boost::multi_index::safe_mode::safe_iterator<Iterator>
>
{
BOOST_STATIC_CONSTANT(

View File

@ -89,12 +89,6 @@ template<
>
class hashed_index:
BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS SuperMeta::type
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,public safe_mode::safe_container<
hashed_index<KeyFromValue,Hash,Pred,SuperMeta,TagList,Category> >
#endif
{
#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)&&\
BOOST_WORKAROUND(__MWERKS__,<=0x3003)
@ -155,8 +149,7 @@ public:
hashed_index_iterator<
index_node_type,bucket_array_type,
Category,
hashed_index_global_iterator_tag>,
hashed_index> iterator;
hashed_index_global_iterator_tag> > iterator;
#else
typedef hashed_index_iterator<
index_node_type,bucket_array_type,
@ -198,8 +191,7 @@ protected:
private:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef safe_mode::safe_container<
hashed_index> safe_super;
typedef safe_mode::safe_container<iterator> safe_container;
#endif
typedef typename call_traits<value_type>::param_type value_param_type;
@ -757,6 +749,11 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
eq_(tuples::get<3>(args_list.get_head())),
buckets(al,header()->impl(),tuples::get<0>(args_list.get_head())),
mlf(1.0f)
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,safe(*this)
#endif
{
calculate_max_load();
}
@ -764,17 +761,17 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
hashed_index(
const hashed_index<KeyFromValue,Hash,Pred,SuperMeta,TagList,Category>& x):
super(x),
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super(),
#endif
key(x.key),
hash_(x.hash_),
eq_(x.eq_),
buckets(x.get_allocator(),header()->impl(),x.buckets.size()),
mlf(x.mlf),
max_load(x.max_load)
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,safe(*this)
#endif
{
/* Copy ctor just takes the internal configuration objects from x. The rest
* is done in subsequent call to copy_().
@ -785,16 +782,16 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
const hashed_index<KeyFromValue,Hash,Pred,SuperMeta,TagList,Category>& x,
do_not_copy_elements_tag):
super(x,do_not_copy_elements_tag()),
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super(),
#endif
key(x.key),
hash_(x.hash_),
eq_(x.eq_),
buckets(x.get_allocator(),header()->impl(),0),
mlf(1.0f)
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,safe(*this)
#endif
{
calculate_max_load();
}
@ -807,12 +804,12 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
iterator make_iterator(index_node_type* node)
{
return iterator(node,this);
return iterator(node,&safe);
}
const_iterator make_iterator(index_node_type* node)const
{
return const_iterator(node,const_cast<hashed_index*>(this));
return const_iterator(node,const_cast<safe_container*>(&safe));
}
#else
iterator make_iterator(index_node_type* node)
@ -1015,7 +1012,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
buckets.clear(header()->impl());
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::detach_dereferenceable_iterators();
safe.detach_dereferenceable_iterators();
#endif
}
@ -1032,7 +1029,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
std::swap(max_load,x.max_load);
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::swap(x);
safe.swap(x.safe);
#endif
super::swap_(x,swap_allocators);
@ -1046,7 +1043,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
std::swap(max_load,x.max_load);
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::swap(x);
safe.swap(x.safe);
#endif
super::swap_elements_(x);
@ -1777,6 +1774,10 @@ private:
float mlf;
size_type max_load;
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_container safe;
#endif
#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)&&\
BOOST_WORKAROUND(__MWERKS__,<=0x3003)
#pragma parse_mfunc_templ reset

View File

@ -81,12 +81,6 @@ namespace detail{
template<typename SuperMeta,typename TagList>
class random_access_index:
BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS SuperMeta::type
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,public safe_mode::safe_container<
random_access_index<SuperMeta,TagList> >
#endif
{
#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)&&\
BOOST_WORKAROUND(__MWERKS__,<=0x3003)
@ -127,8 +121,7 @@ public:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef safe_mode::safe_iterator<
rnd_node_iterator<index_node_type>,
random_access_index> iterator;
rnd_node_iterator<index_node_type> > iterator;
#else
typedef rnd_node_iterator<index_node_type> iterator;
#endif
@ -175,8 +168,7 @@ protected:
private:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef safe_mode::safe_container<
random_access_index> safe_super;
typedef safe_mode::safe_container<iterator> safe_container;
#endif
typedef typename call_traits<
@ -760,17 +752,22 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
const ctor_args_list& args_list,const allocator_type& al):
super(args_list.get_tail(),al),
ptrs(al,header()->impl(),0)
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,safe(*this)
#endif
{
}
random_access_index(const random_access_index<SuperMeta,TagList>& x):
super(x),
ptrs(x.get_allocator(),header()->impl(),x.size())
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super(),
,safe(*this)
#endif
ptrs(x.get_allocator(),header()->impl(),x.size())
{
/* The actual copying takes place in subsequent call to copy_().
*/
@ -779,12 +776,12 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
random_access_index(
const random_access_index<SuperMeta,TagList>& x,do_not_copy_elements_tag):
super(x,do_not_copy_elements_tag()),
ptrs(x.get_allocator(),header()->impl(),0)
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super(),
,safe(*this)
#endif
ptrs(x.get_allocator(),header()->impl(),0)
{
}
@ -795,9 +792,9 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
iterator make_iterator(index_node_type* node)
{return iterator(node,this);}
{return iterator(node,&safe);}
const_iterator make_iterator(index_node_type* node)const
{return const_iterator(node,const_cast<random_access_index*>(this));}
{return const_iterator(node,const_cast<safe_container*>(&safe));}
#else
iterator make_iterator(index_node_type* node){return iterator(node);}
const_iterator make_iterator(index_node_type* node)const
@ -868,7 +865,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
ptrs.clear();
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::detach_dereferenceable_iterators();
safe.detach_dereferenceable_iterators();
#endif
}
@ -879,7 +876,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
ptrs.swap(x.ptrs,swap_allocators);
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::swap(x);
safe.swap(x.safe);
#endif
super::swap_(x,swap_allocators);
@ -890,7 +887,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
ptrs.swap(x.ptrs);
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::swap(x);
safe.swap(x.safe);
#endif
super::swap_elements_(x);
@ -1210,6 +1207,10 @@ private:
ptr_array ptrs;
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_container safe;
#endif
#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)&&\
BOOST_WORKAROUND(__MWERKS__,<=0x3003)
#pragma parse_mfunc_templ reset

View File

@ -71,12 +71,6 @@ namespace detail{
template<typename SuperMeta,typename TagList>
class sequenced_index:
BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS SuperMeta::type
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,public safe_mode::safe_container<
sequenced_index<SuperMeta,TagList> >
#endif
{
#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)&&\
BOOST_WORKAROUND(__MWERKS__,<=0x3003)
@ -114,8 +108,7 @@ public:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef safe_mode::safe_iterator<
bidir_node_iterator<index_node_type>,
sequenced_index> iterator;
bidir_node_iterator<index_node_type> > iterator;
#else
typedef bidir_node_iterator<index_node_type> iterator;
#endif
@ -162,8 +155,7 @@ protected:
private:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef safe_mode::safe_container<
sequenced_index> safe_super;
typedef safe_mode::safe_container<iterator> safe_container;
#endif
typedef typename call_traits<value_type>::param_type value_param_type;
@ -674,6 +666,11 @@ public:
BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
sequenced_index(const ctor_args_list& args_list,const allocator_type& al):
super(args_list.get_tail(),al)
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,safe(*this)
#endif
{
empty_initialize();
}
@ -682,7 +679,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
super(x)
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,safe_super()
,safe(*this)
#endif
{
@ -694,7 +691,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
super(x,do_not_copy_elements_tag())
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
,safe_super()
,safe(*this)
#endif
{
@ -708,9 +705,9 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
iterator make_iterator(index_node_type* node)
{return iterator(node,this);}
{return iterator(node,&safe);}
const_iterator make_iterator(index_node_type* node)const
{return const_iterator(node,const_cast<sequenced_index*>(this));}
{return const_iterator(node,const_cast<safe_container*>(&safe));}
#else
iterator make_iterator(index_node_type* node){return iterator(node);}
const_iterator make_iterator(index_node_type* node)const
@ -781,7 +778,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
empty_initialize();
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::detach_dereferenceable_iterators();
safe.detach_dereferenceable_iterators();
#endif
}
@ -790,7 +787,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
sequenced_index<SuperMeta,TagList>& x,BoolConstant swap_allocators)
{
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::swap(x);
safe.swap(x.safe);
#endif
super::swap_(x,swap_allocators);
@ -799,7 +796,7 @@ BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
void swap_elements_(sequenced_index<SuperMeta,TagList>& x)
{
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_super::swap(x);
safe.swap(x.safe);
#endif
super::swap_elements_(x);
@ -1118,6 +1115,10 @@ private:
}
}
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
safe_container safe;
#endif
#if defined(BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING)&&\
BOOST_WORKAROUND(__MWERKS__,<=0x3003)
#pragma parse_mfunc_templ reset

View File

@ -489,9 +489,7 @@ public:
#endif
BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(it);
BOOST_MULTI_INDEX_CHECK_IS_OWNER(
it,static_cast<typename IteratorType::container_type&>(*this));
BOOST_MULTI_INDEX_CHECK_BELONGS_IN_SOME_INDEX(it,*this);
return index_type::make_iterator(
static_cast<final_node_type*>(it.get_node()));
}
@ -508,8 +506,7 @@ public:
#endif
BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(it);
BOOST_MULTI_INDEX_CHECK_IS_OWNER(
it,static_cast<const typename IteratorType::container_type&>(*this));
BOOST_MULTI_INDEX_CHECK_BELONGS_IN_SOME_INDEX(it,*this);
return index_type::make_iterator(
static_cast<final_node_type*>(it.get_node()));
}
@ -541,8 +538,7 @@ public:
#endif
BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(it);
BOOST_MULTI_INDEX_CHECK_IS_OWNER(
it,static_cast<typename IteratorType::container_type&>(*this));
BOOST_MULTI_INDEX_CHECK_BELONGS_IN_SOME_INDEX(it,*this);
return index_type::make_iterator(
static_cast<final_node_type*>(it.get_node()));
}
@ -559,8 +555,7 @@ public:
#endif
BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(it);
BOOST_MULTI_INDEX_CHECK_IS_OWNER(
it,static_cast<const typename IteratorType::container_type&>(*this));
BOOST_MULTI_INDEX_CHECK_BELONGS_IN_SOME_INDEX(it,*this);
return index_type::make_iterator(
static_cast<final_node_type*>(it.get_node()));
}
@ -1362,14 +1357,7 @@ project(
#endif
BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(it);
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef detail::converter<
multi_index_type,
BOOST_DEDUCED_TYPENAME IteratorType::container_type> converter;
BOOST_MULTI_INDEX_CHECK_IS_OWNER(it,converter::index(m));
#endif
BOOST_MULTI_INDEX_CHECK_BELONGS_IN_SOME_INDEX(it,m);
return detail::converter<multi_index_type,index_type>::iterator(
m,static_cast<typename multi_index_type::final_node_type*>(it.get_node()));
}
@ -1398,14 +1386,7 @@ project(
#endif
BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(it);
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef detail::converter<
multi_index_type,
BOOST_DEDUCED_TYPENAME IteratorType::container_type> converter;
BOOST_MULTI_INDEX_CHECK_IS_OWNER(it,converter::index(m));
#endif
BOOST_MULTI_INDEX_CHECK_BELONGS_IN_SOME_INDEX(it,m);
return detail::converter<multi_index_type,index_type>::const_iterator(
m,static_cast<typename multi_index_type::final_node_type*>(it.get_node()));
}
@ -1448,14 +1429,7 @@ project(
#endif
BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(it);
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef detail::converter<
multi_index_type,
BOOST_DEDUCED_TYPENAME IteratorType::container_type> converter;
BOOST_MULTI_INDEX_CHECK_IS_OWNER(it,converter::index(m));
#endif
BOOST_MULTI_INDEX_CHECK_BELONGS_IN_SOME_INDEX(it,m);
return detail::converter<multi_index_type,index_type>::iterator(
m,static_cast<typename multi_index_type::final_node_type*>(it.get_node()));
}
@ -1485,14 +1459,7 @@ project(
#endif
BOOST_MULTI_INDEX_CHECK_VALID_ITERATOR(it);
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
typedef detail::converter<
multi_index_type,
BOOST_DEDUCED_TYPENAME IteratorType::container_type> converter;
BOOST_MULTI_INDEX_CHECK_IS_OWNER(it,converter::index(m));
#endif
BOOST_MULTI_INDEX_CHECK_BELONGS_IN_SOME_INDEX(it,m);
return detail::converter<multi_index_type,index_type>::const_iterator(
m,static_cast<typename multi_index_type::final_node_type*>(it.get_node()));
}