Subversion Repositories Kolibri OS

Rev

Blame | Last modification | View Log | RSS feed

  1. // Guarded Allocation -*- C++ -*-
  2.  
  3. // Copyright (C) 2014-2015 Free Software Foundation, Inc.
  4. //
  5. // This file is part of the GNU ISO C++ Library.  This library is free
  6. // software; you can redistribute it and/or modify it under the
  7. // terms of the GNU General Public License as published by the
  8. // Free Software Foundation; either version 3, or (at your option)
  9. // any later version.
  10.  
  11. // This library is distributed in the hope that it will be useful,
  12. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14. // GNU General Public License for more details.
  15.  
  16. // Under Section 7 of GPL version 3, you are granted additional
  17. // permissions described in the GCC Runtime Library Exception, version
  18. // 3.1, as published by the Free Software Foundation.
  19.  
  20. // You should have received a copy of the GNU General Public License and
  21. // a copy of the GCC Runtime Library Exception along with this program;
  22. // see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
  23. // <http://www.gnu.org/licenses/>.
  24.  
  25. /** @file bits/allocated_ptr.h
  26.  *  This is an internal header file, included by other library headers.
  27.  *  Do not attempt to use it directly. @headername{memory}
  28.  */
  29.  
  30. #ifndef _ALLOCATED_PTR_H
  31. #define _ALLOCATED_PTR_H 1
  32.  
  33. #if __cplusplus < 201103L
  34. # include <bits/c++0xwarning.h>
  35. #else
  36. # include <type_traits>
  37. # include <bits/ptr_traits.h>
  38. # include <bits/alloc_traits.h>
  39.  
  40. namespace std _GLIBCXX_VISIBILITY(default)
  41. {
  42. _GLIBCXX_BEGIN_NAMESPACE_VERSION
  43.  
  44.   /// Non-standard RAII type for managing pointers obtained from allocators.
  45.   template<typename _Alloc>
  46.     struct __allocated_ptr
  47.     {
  48.       using pointer = typename allocator_traits<_Alloc>::pointer;
  49.       using value_type = typename allocator_traits<_Alloc>::value_type;
  50.  
  51.       /// Take ownership of __ptr
  52.       __allocated_ptr(_Alloc& __a, pointer __ptr) noexcept
  53.       : _M_alloc(&__a), _M_ptr(__ptr)
  54.       { }
  55.  
  56.       /// Convert __ptr to allocator's pointer type and take ownership of it
  57.       template<typename _Ptr,
  58.                typename _Req = _Require<is_same<_Ptr, value_type*>>>
  59.       __allocated_ptr(_Alloc& __a, _Ptr __ptr)
  60.       : _M_alloc(&__a), _M_ptr(pointer_traits<pointer>::pointer_to(*__ptr))
  61.       { }
  62.  
  63.       /// Transfer ownership of the owned pointer
  64.       __allocated_ptr(__allocated_ptr&& __gd) noexcept
  65.       : _M_alloc(__gd._M_alloc), _M_ptr(__gd._M_ptr)
  66.       { __gd._M_ptr = nullptr; }
  67.  
  68.       /// Deallocate the owned pointer
  69.       ~__allocated_ptr()
  70.       {
  71.         if (_M_ptr != nullptr)
  72.           std::allocator_traits<_Alloc>::deallocate(*_M_alloc, _M_ptr, 1);
  73.       }
  74.  
  75.       /// Release ownership of the owned pointer
  76.       __allocated_ptr&
  77.       operator=(std::nullptr_t) noexcept
  78.       {
  79.         _M_ptr = nullptr;
  80.         return *this;
  81.       }
  82.  
  83.       /// Get the address that the owned pointer refers to.
  84.       value_type* get() { return _S_raw_ptr(_M_ptr); }
  85.  
  86.     private:
  87.       value_type* _S_raw_ptr(value_type* __ptr) { return __ptr; }
  88.  
  89.       template<typename _Ptr>
  90.         auto _S_raw_ptr(_Ptr __ptr) -> decltype(_S_raw_ptr(__ptr.operator->()))
  91.         { return _S_raw_ptr(__ptr.operator->()); }
  92.  
  93.       _Alloc* _M_alloc;
  94.       pointer _M_ptr;
  95.     };
  96.  
  97.   /// Allocate space for a single object using __a
  98.   template<typename _Alloc>
  99.     __allocated_ptr<_Alloc>
  100.     __allocate_guarded(_Alloc& __a)
  101.     {
  102.       return { __a, std::allocator_traits<_Alloc>::allocate(__a, 1) };
  103.     }
  104.  
  105. _GLIBCXX_END_NAMESPACE_VERSION
  106. } // namespace std
  107.  
  108. #endif
  109. #endif
  110.