1 #ifndef LIBJMMCG_CORE_INTRUSIVE_HPP
2 #define LIBJMMCG_CORE_INTRUSIVE_HPP
30 template<
class,
class>
class slist_iterator_internal;
33 template<
class,
class>
class stack;
34 template<
class,
class>
class slist;
46 using lock_traits=LkT;
47 using atomic_ctr_t=base_t;
70 class node_details
final :
public node_details_itf<LkT>,
public sp_counter_type<
typename node_details_itf<LkT>::atomic_ctr_t::value_type,
typename node_details_itf<LkT>::lock_traits> {
73 using base2_t=sp_counter_type<
typename base_t::atomic_ctr_t::value_type,
typename base_t::lock_traits>;
74 using atomic_ctr_t=
typename base2_t::atomic_ctr_t;
75 using lock_traits=
typename base_t::lock_traits;
85 return base2_t::sp_to_string();
89 template<
class V,
class LkT>
struct end;
94 template<
class V,
class LkT>
95 class slist_iterator_internal {
97 using lock_traits=LkT;
113 BOOST_MPL_ASSERT((
std::is_base_of<
typename node_ptr_t::value_type,
typename value_type::value_type>));
118 real_node(node.get().get() ? node->next : node.get()) {
119 assert(node.get().get() ? node->next==real_node.get() :
true);
123 real_node(node.get().get() ? node->next : node.get()) {
127 real_node=n.real_node;
132 if (node.get().get() && n.node.get().get()) {
133 return node->next==n.node->next;
134 }
else if (!node.get() && !n.node.get()) {
136 }
else if (node.get().get() && !n.node.get()) {
137 return node->next==n.node.get();
143 return !operator==(n);
148 const typename node_ptr_t::atomic_ptr_t next_real_node(real_node.get().get() ? real_node->next :
typename node_ptr_t::atomic_ptr_t());
150 real_node=node_ptr_t(next_real_node);
151 assert(node.get().get() ? node->next==real_node.get() :
true);
155 const slist_iterator_internal tmp(*
this);
173 operator<<(
tostream &os, slist_iterator_internal
const &i) {
175 <<
", real_node="<<i.real_node;
180 friend class stack<V, LkT>;
181 friend class slist<V, LkT>;
187 node_ptr_t real_node;
189 template<
class V,
class LkT>
190 class slist_iterator_internal<V
const, LkT> {
192 using lock_traits=LkT;
208 BOOST_MPL_ASSERT((
std::is_base_of<
typename node_ptr_t::value_type,
typename value_type::value_type>));
212 : node(n), real_node(node.get().get() ? node->next : node.get()) {
213 assert(node.get().get() ? node->next==real_node.get().get() :
true);
216 : node(n), real_node(node.get().get() ? node->next : node.get()) {
217 assert(node.get().get() ? node->next==real_node.get() :
true);
220 : node(n.node), real_node(node.get().get() ? node->next : node.get()) {
224 if (node.get().get() && n.node.get().get()) {
225 return node->next==n.node->next;
226 }
else if (!node.get() && !n.node.get()) {
228 }
else if (node.get().get() && !n.node.get()) {
229 return node->next==n.node.get();
239 const typename node_ptr_t::atomic_ptr_t next_real_node(real_node.get().get() ? real_node->next :
typename node_ptr_t::atomic_ptr_t());
241 real_node=node_ptr_t(next_real_node);
242 assert(node.get().get() ? node->next==real_node.get() :
true);
246 const slist_iterator_internal tmp(*
this);
258 operator<<(
tostream &os, slist_iterator_internal
const &i) {
260 <<
", real_node="<<i.real_node;
265 friend class stack<V, LkT>;
266 friend class slist<V, LkT>;
272 node_ptr_t real_node;
275 template<
class V,
class LkT>
276 struct end
final :
public slist_iterator_internal<V, LkT> {
277 typedef slist_iterator_internal<V, LkT>
base_t;
292 slist_iterator_internal<V, LkT>::
operator==(end<V, LkT>
const &n)
const noexcept(
true) {
293 return node.get().get() ? node->next==n.node.get().get() : !node.get();
312 using atomic_ptr_t=
typename node_details_t::base_t::atomic_ptr_t;
315 using lock_traits=
typename node_details_t::lock_traits;
340 BOOST_MPL_ASSERT((
std::is_base_of<
typename node_details_t::base_t,
typename value_type::value_type>));
489 class slist :
public stack<V, LkT> {
598 typedef typename base_t::node_details_t node_details_t;
604 typename node_details_t::base_t::atomic_ptr_t penultimate_;
606 static void move_penultimate(
typename node_details_t::base_t::atomic_ptr_t &ptr)
noexcept(
true)
FORCE_INLINE;