summaryrefslogtreecommitdiff
path: root/libcult/cult/mm/bits/evptr.hxx
diff options
context:
space:
mode:
Diffstat (limited to 'libcult/cult/mm/bits/evptr.hxx')
-rw-r--r--libcult/cult/mm/bits/evptr.hxx379
1 files changed, 0 insertions, 379 deletions
diff --git a/libcult/cult/mm/bits/evptr.hxx b/libcult/cult/mm/bits/evptr.hxx
deleted file mode 100644
index 02f0b48..0000000
--- a/libcult/cult/mm/bits/evptr.hxx
+++ /dev/null
@@ -1,379 +0,0 @@
-// file : cult/mm/bits/evptr.hxx
-// author : Boris Kolpackov <boris@kolpackov.net>
-// copyright : Copyright (c) 2005-2010 Boris Kolpackov
-// license : GNU GPL v2 + exceptions; see accompanying LICENSE file
-
-#ifndef CULT_MM_BITS_EVPTR_HXX
-#define CULT_MM_BITS_EVPTR_HXX
-
-#include <cult/types/fundamental.hxx>
-
-#include <cult/meta/answer.hxx>
-
-#include <cult/mm/counter.hxx>
-#include <cult/mm/exception.hxx>
-
-#include <cassert> // assert
-
-namespace Cult
-{
- namespace MM
- {
-
- //@@ Should be in mm/evptr.hxx
- //
- struct Clone: virtual Exception {};
-
- template <typename X>
- class Evptr;
-
- namespace Bits
- {
- template <typename x, Evptr<x> (x::*f) () const = &x::clone>
- struct Helper;
-
- //@@ Should be generalized and moved to Cult::meta
- //
- template <typename X>
- struct has_clone
- {
- template <typename y>
- static Meta::Yes
- test (Helper<y>*);
-
- template <typename>
- static Meta::No
- test (...);
-
- static Boolean const r = sizeof (test<X> (0)) == sizeof (Meta::Yes);
- };
-
- //@@ Need to incorporate tests for polymorpism and NonCopyable.
- //
-
- template <typename X, Boolean = has_clone<X>::r>
- struct Cloner;
-
- template <typename X>
- struct Cloner<X, true>
- {
- static X*
- clone (X const* cp)
- {
- return cp->clone ().release ();
- }
- };
-
- template <typename X>
- struct Cloner<X, false>
- {
- static X*
- clone (X const*)
- {
- throw MM::Clone ();
- }
- };
- }
-
- namespace Bits
- {
- template <typename X>
- class Transfer;
- }
-
- namespace Bits
- {
- template <typename X>
- class EvptrBase
- {
- protected:
- ~EvptrBase ()
- {
- free (p_ ? p_ : cp_, c_);
- }
-
- EvptrBase (X* p, X const* cp, Counter* c, Boolean inc = true)
- : p_ (p), cp_ (cp), c_ (c)
- {
- assert (!(p_ != 0 && cp_ != 0));
-
- if (cp_ != 0 && c_ && inc) c_->inc_ref ();
- }
-
- public:
- X*
- get () const
- {
- return get_ ();
- }
-
- X*
- release ()
- {
- X* p (get_ ());
-
- c_ = 0;
- p_ = 0;
- cp_ = 0;
-
- return p;
- }
-
- Size
- count () const
- {
- if (c_ == 0) throw NullPointer ();
- return c_->count ();
- }
-
- public:
- // Conversion to Boolean.
- //
- typedef X* (EvptrBase::*BooleanConvertible)() const;
-
- operator BooleanConvertible () const
- {
- return c_ ? &EvptrBase::get : 0;
- }
-
- protected:
- Void
- assign (X const* cp, Counter* c)
- {
- if (c_ && c_ == c) throw SelfAssignment ();
-
- free (p_ ? p_ : cp_, c_);
-
- if (c) c->inc_ref ();
-
- c_ = c;
- p_ = 0;
- cp_ = cp;
- }
-
- Void
- transfer (X* p, X const* cp, Counter* c)
- {
- free (p_ ? p_ : cp_, c_);
-
- c_ = c;
- p_ = p;
- cp_ = cp;
- }
-
- protected:
- X*
- get_ () const
- {
- if (c_ == 0) return 0;
-
- assert (p_ != 0 || cp_ != 0);
-
- if (p_ != 0)
- {
- if (c_->count () == 1) return p_;
- else
- {
- // Convert to shared case.
- //
- cp_ = p_;
- p_ = 0;
- }
- }
-
- // Shared case with cloning.
- //
-
- // Check if we are the sole owner.
- //
- if (c_->count () == 1)
- {
- // Convert to exclusive case.
- //
- p_ = const_cast<X*> (cp_);
- cp_ = 0;
- }
- else
- {
- assert (cp_ != 0);
-
- //p_ = cp_->clone ().release ();
-
- p_ = Cloner<X>::clone (cp_);
-
- free (cp_, c_);
-
- cp_ = 0;
- c_ = locate (p_, *counted);
- }
-
- return p_;
- }
-
- static Void
- free (X const* p, Counter* c)
- {
- if (c && c->dec_ref ())
- {
- assert (p != 0);
- delete p;
- }
- }
-
- private:
- template <typename>
- friend class Evptr;
-
- template <typename>
- friend class Transfer;
-
- mutable X* p_;
- mutable X const* cp_;
- mutable Counter* c_;
- };
-
-
- template <typename X>
- class EvptrBase<X const>
- {
- protected:
- ~EvptrBase ()
- {
- free (p_ ? p_ : cp_, c_);
- }
-
- EvptrBase (X const* p, X const* cp, Counter* c, Boolean inc = true)
- : p_ (p), cp_ (cp), c_ (c)
- {
- assert (!(p_ != 0 && cp_ != 0));
-
- if (cp_ != 0 && c_ && inc) c_->inc_ref ();
- }
-
- public:
- X const*
- get ()
- {
- return get_ ();
- }
-
- //@@ Should clone if shared?
- //
- X const*
- release ()
- {
- X const* p (get_ ());
-
- c_ = 0;
- p_ = 0;
- cp_ = 0;
-
- return p;
- }
-
- Size
- count () const
- {
- if (c_ == 0) throw NullPointer ();
- return c_->count ();
- }
-
- public:
- // Conversion to Boolean.
- //
- typedef X const* (EvptrBase::*BooleanConvertible)() const;
-
- operator BooleanConvertible () const
- {
- return c_ ? &EvptrBase::get : 0;
- }
-
- protected:
- Void
- assign (X const* cp, Counter* c)
- {
- if (c_ && c_ == c) throw SelfAssignment ();
-
- free (p_ ? p_ : cp_, c_);
-
- if (c) c->inc_ref ();
-
- c_ = c;
- p_ = 0;
- cp_ = cp;
- }
-
- Void
- transfer (X const* p, X const* cp, Counter* c)
- {
- free (p_ ? p_ : cp_, c_);
-
- c_ = c;
- p_ = p;
- cp_ = cp;
- }
-
- protected:
- X const*
- get_ () const
- {
- return p_ ? p_ : cp_;
- }
-
- static Void
- free (X const* p, Counter* c)
- {
- if (c && c->dec_ref ())
- {
- assert (p != 0);
- delete p;
- }
- }
-
- private:
- template <typename>
- friend class Evptr;
-
- template <typename>
- friend class Transfer;
-
- mutable X const* p_;
- mutable X const* cp_;
- mutable Counter* c_;
- };
- }
-
- namespace Bits
- {
- template <typename X>
- class Transfer : protected EvptrBase<X>
- {
- public:
- Transfer (Transfer<X> const& ct)
- : EvptrBase<X> (ct.p_, ct.cp_, ct.c_, false)
- {
- Transfer<X>& t (const_cast<Transfer<X>&> (ct));
-
- t.c_ = 0;
- t.p_ = 0;
- t.cp_ = 0;
- }
-
- private:
- Transfer (X* p, X const* cp, Counter* c)
- : EvptrBase<X> (p, cp, c, false)
- {
- }
-
- template <typename>
- friend class Evptr;
-
- private:
- Transfer<X>&
- operator= (Transfer<X> const&);
- };
- }
- }
-}
-
-#endif // CULT_MM_BITS_EVPTR_HXX