/*=========================================================================

  Program:   KWSys - Kitware System Library
  Module:    $RCSfile: auto_ptr.hxx.in,v $

  Copyright (c) Kitware, Inc., Insight Consortium.  All rights reserved.
  See Copyright.txt or http://www.kitware.com/Copyright.htm for details.

     This software is distributed WITHOUT ANY WARRANTY; without even
     the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
     PURPOSE.  See the above copyright notices for more information.

=========================================================================*/
#ifndef @KWSYS_NAMESPACE@_auto_ptr_hxx
#define @KWSYS_NAMESPACE@_auto_ptr_hxx

#include <@KWSYS_NAMESPACE@/Configure.hxx>

// The HP compiler and VS6 cannot handle the conversions necessary to use
// auto_ptr_ref to pass an auto_ptr returned from one function
// directly to another function as in use_auto_ptr(get_auto_ptr()).
// We instead use const_cast to achieve the syntax on those platforms.
// We do not use const_cast on other platforms to maintain the C++
// standard design and guarantee that if an auto_ptr is bound
// to a reference-to-const then ownership will be maintained.
#if defined(__HP_aCC) || (defined(_MSC_VER) && _MSC_VER <= 1200)
# define @KWSYS_NAMESPACE@_AUTO_PTR_REF 0
# define @KWSYS_NAMESPACE@_AUTO_PTR_CONST const
# define @KWSYS_NAMESPACE@_AUTO_PTR_CAST(a) cast(a)
#else
# define @KWSYS_NAMESPACE@_AUTO_PTR_REF 1
# define @KWSYS_NAMESPACE@_AUTO_PTR_CONST
# define @KWSYS_NAMESPACE@_AUTO_PTR_CAST(a) a
#endif

namespace @KWSYS_NAMESPACE@
{

template <class X> class auto_ptr;

#if @KWSYS_NAMESPACE@_AUTO_PTR_REF
namespace detail
{
// The auto_ptr_ref template is supposed to be a private member of
// auto_ptr but Borland 5.8 cannot handle it.  Instead put it in
// a private namespace.
template <class Y> struct auto_ptr_ref
{
  Y* p_;

  // The extra constructor argument prevents implicit conversion to
  // auto_ptr_ref from auto_ptr through the constructor.  Normally
  // this should be done with the explicit keyword but Borland 5.x
  // generates code in the conversion operator to call itself
  // infinately.
  auto_ptr_ref(Y* p, int): p_(p) {}
};
}
#endif

/** C++98 Standard Section 20.4.5 - Template class auto_ptr.  */
template <class X>
class auto_ptr
{
#if !@KWSYS_NAMESPACE@_AUTO_PTR_REF
  template <typename Y>
  static inline auto_ptr<Y>& cast(auto_ptr<Y> const& a)
    { return const_cast<auto_ptr<Y>&>(a); }
#endif

  /** The pointer to the object held.  */
  X* x_;

public:
  /** The type of object held by the auto_ptr.  */
  typedef X element_type;

  /** Construct from an auto_ptr holding a compatible object.  This
      transfers ownership to the newly constructed auto_ptr.  */
  template <class Y>
  auto_ptr(auto_ptr<Y> @KWSYS_NAMESPACE@_AUTO_PTR_CONST& a) throw():
    x_(@KWSYS_NAMESPACE@_AUTO_PTR_CAST(a).release())
    {
    }

  /** Assign from an auto_ptr holding a compatible object.  This
      transfers ownership to the left-hand-side of the assignment.  */
  template <class Y>
  auto_ptr& operator=(auto_ptr<Y> @KWSYS_NAMESPACE@_AUTO_PTR_CONST& a) throw()
    {
    this->reset(@KWSYS_NAMESPACE@_AUTO_PTR_CAST(a).release());
    return *this;
    }

  /**
   * Explicitly construct from a raw pointer.  This is typically
   * called with the result of operator new.  For example:
   *
   *   auto_ptr<X> ptr(new X());
   */
  explicit auto_ptr(X* p=0) throw(): x_(p)
    {
    }

  /** Construct from another auto_ptr holding an object of the same
      type.  This transfers ownership to the newly constructed
      auto_ptr.  */
  auto_ptr(auto_ptr @KWSYS_NAMESPACE@_AUTO_PTR_CONST& a) throw():
    x_(@KWSYS_NAMESPACE@_AUTO_PTR_CAST(a).release())
    {
    }

  /** Assign from another auto_ptr holding an object of the same type.
      This transfers ownership to the newly constructed auto_ptr.  */
  auto_ptr& operator=(auto_ptr @KWSYS_NAMESPACE@_AUTO_PTR_CONST& a) throw()
    {
    this->reset(@KWSYS_NAMESPACE@_AUTO_PTR_CAST(a).release());
    return *this;
    }

  /** Destruct and delete the object held.  */
  ~auto_ptr() throw()
    {
    // Assume object destructor is nothrow.
    delete this->x_;
    }

  /** Dereference and return a reference to the object held.  */
  X& operator*() const throw()
    {
    return *this->x_;
    }

  /** Return a pointer to the object held.  */
  X* operator->() const throw()
    {
    return this->x_;
    }

  /** Return a pointer to the object held.  */
  X* get() const throw()
    {
    return this->x_;
    }

  /** Return a pointer to the object held and reset to hold no object.
      This transfers ownership to the caller.  */
  X* release() throw()
    {
    X* x = this->x_;
    this->x_ = 0;
    return x;
    }

  /** Assume ownership of the given object.  The object previously
      held is deleted.  */
  void reset(X* p=0) throw()
    {
    if(this->x_ != p)
      {
      // Assume object destructor is nothrow.
      delete this->x_;
      this->x_ = p;
      }
    }

  /** Convert to an auto_ptr holding an object of a compatible type.
      This transfers ownership to the returned auto_ptr.  */
  template <class Y> operator auto_ptr<Y>() throw()
    {
    return auto_ptr<Y>(this->release());
    }

#if @KWSYS_NAMESPACE@_AUTO_PTR_REF
  /** Construct from an auto_ptr_ref.  This is used when the
      constructor argument is a call to a function returning an
      auto_ptr.  */
  auto_ptr(detail::auto_ptr_ref<X> r) throw(): x_(r.p_)
    {
    }

  /** Assign from an auto_ptr_ref.  This is used when a function
      returning an auto_ptr is passed on the right-hand-side of an
      assignment.  */
  auto_ptr& operator=(detail::auto_ptr_ref<X> r) throw()
    {
    this->reset(r.p_);
    return *this;
    }

  /** Convert to an auto_ptr_ref.  This is used when a function
      returning an auto_ptr is the argument to the constructor of
      another auto_ptr.  */
  template <class Y> operator detail::auto_ptr_ref<Y>() throw()
    {
    return detail::auto_ptr_ref<Y>(this->release(), 1);
    }
#endif
};

} // namespace @KWSYS_NAMESPACE@

#endif
