Sven Rosvall
Home - Contact Info
 Start
 Sven Rosvall
   CV
   Projects
   Articles
     Mixing Strings in C++
     C++ as a Safer C
       Listing 1
       Listing 2
       Listing 3
     C++ Lookup Mysteries
 Kari Rosvall
 The Rosvalls

Listing 3

// BoundedPointer.h
// Bounds checked pointer
//

#ifndef BoundedPointer_h
#define BoundedPointer_h

#include <cstddef>
#include <cassert>


template <typename T>
class BoundedPointer
{
public:
  // Default constructor
  BoundedPointer()
#ifndef NDEBUG
    : m_initialised(false)
#endif
    {}

  // Constructor from a pointer
  BoundedPointer(const T * value)
    : m_p(const_cast<T *>(value))
#ifndef NDEBUG
    , m_base(m_p)
    , m_size(1)
    , m_initialised(true)
#endif
    {}

  // Constructor from a built-in array
  template <size_t Size>
  BoundedPointer(T (&arr)[Size])
    : m_p(arr)
#ifndef NDEBUG
    , m_base(m_p)
    , m_size(Size)
    , m_initialised(true)
#endif
    {}

  // Constructor from an user defined array type
  BoundedPointer(const T * base, size_t size)
    : m_p(const_cast<T *>(base))
#ifndef NDEBUG
    , m_base(m_p)
    , m_size(size)
    , m_initialised(true)
#endif
    {}

  // Dereference operators
  T & operator*()
    {
      assert(m_initialised);
      assert(m_p != 0);
      return *m_p;
    }
  T * operator->()
    {
      assert(m_initialised);
      assert(m_p != 0);
      return m_p;
    }
  T & operator[](size_t ix)
    {
      assert(m_initialised);
      assert(m_p != 0);
      assert(ix < m_size - (m_p-m_base));
      return m_p[ix];
    }

  // Pointer arithmetic operations
  ptrdiff_t operator-(BoundedPointer const & rhs)
    {
      // Check validity of the pointers
      assert(m_initialised);
      assert(rhs.m_initialised);
      assert(m_p != 0);
      assert(rhs.m_p != 0);

      // Make sure that both pointer point 
      // to the same array
      assert(m_base == rhs.m_base);
      return m_p - rhs.m_p;
    }
  BoundedPointer & operator+=(ptrdiff_t rhs)
    {
      // Check validity of the pointers
      assert(m_initialised);
      assert(m_p != 0);

      m_p += rhs;
      assert(m_base <= m_p && m_p < m_base + m_size);
      return *this;
    }
  BoundedPointer & operator-=(int rhs)
    {
      // Check validity of the pointers
      assert(m_initialised);
      assert(m_p != 0);

      m_p -= rhs;
      assert(m_p >= m_base);
      return *this;
    }
  BoundedPointer & operator++()
    {
      // Check validity of the pointers
      assert(m_initialised);
      assert(m_p != 0);

      ++m_p;
      assert(m_p < m_base + m_size);
      return *this;
    }
  BoundedPointer & operator--()
    {
      // Check validity of the pointers
      assert(m_initialised);
      assert(m_p != 0);

      --m_p;
      assert(m_p >= m_base);
      return *this;
    }

  // Comparison operators
  bool operator<(BoundedPointer const & rhs)
    {
      // Check validity of the pointers
      assert(m_initialised);
      assert(rhs.m_initialised);
      assert(m_p != 0);
      assert(rhs.m_p != 0);

      // Make sure that both pointer point 
      // to the same array
      assert(m_base == rhs.m_base);
      return m_p < rhs.m_p;
    }
  bool operator==(BoundedPointer const & rhs)
    {
      // Check validity of the pointers
      assert(m_initialised);
      assert(rhs.m_initialised);
      assert(m_p != 0);
      assert(rhs.m_p != 0);

      // Make sure that both pointer point 
      // to the same array
      assert(m_base == rhs.m_base);
      return m_p == rhs.m_p;
    }


private:
  T * m_p;
#ifndef NDEBUG
  T * m_base;
  size_t m_size;
  bool m_initialised;
#endif
};

// Binary arithmetic operators
template <typename T>
inline BoundedPointer<T> 
operator+(BoundedPointer<T> lhs, int rhs)
{
  return lhs.operator+=(rhs);
}
template <typename T>
inline BoundedPointer<T> 
operator+(int lhs, BoundedPointer<T> rhs)
{
  return rhs.operator+=(lhs);
}

template <typename T>
inline BoundedPointer<T> 
operator-(BoundedPointer<T> lhs, int rhs)
{
  return lhs.operator-=(rhs);
}
template <typename T>
inline BoundedPointer<T> 
operator-(int lhs, BoundedPointer<T> rhs)
{
  return rhs.operator-=(lhs);
}

#endif


Copyright 2003-2012