allocation.qbk 3.4 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889
  1. [/
  2. / Copyright (c) 2003-2019 Christopher M. Kohlhoff (chris at kohlhoff dot com)
  3. /
  4. / Distributed under the Boost Software License, Version 1.0. (See accompanying
  5. / file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  6. /]
  7. [section:allocation Custom Memory Allocation]
  8. Many asynchronous operations need to allocate an object to store state
  9. associated with the operation. For example, a Win32 implementation needs
  10. `OVERLAPPED`-derived objects to pass to Win32 API functions.
  11. Furthermore, programs typically contain easily identifiable chains of
  12. asynchronous operations. A half duplex protocol implementation (e.g. an HTTP
  13. server) would have a single chain of operations per client (receives followed
  14. by sends). A full duplex protocol implementation would have two chains
  15. executing in parallel. Programs should be able to leverage this knowledge to
  16. reuse memory for all asynchronous operations in a chain.
  17. Given a copy of a user-defined `Handler` object `h`, if the implementation
  18. needs to allocate memory associated with that handler it will obtain an
  19. allocator using the `get_associated_allocator` function. For example:
  20. boost::asio::associated_allocator_t<Handler> a = boost::asio::get_associated_allocator(h);
  21. The associated allocator must satisfy the standard Allocator requirements.
  22. By default, handlers use the standard allocator (which is implemented in terms
  23. of `::operator new()` and `::operator delete()`). The allocator may be
  24. customised for a particular handler type by specifying a nested type
  25. `allocator_type` and member function `get_allocator()`:
  26. class my_handler
  27. {
  28. public:
  29. // Custom implementation of Allocator type requirements.
  30. typedef my_allocator allocator_type;
  31. // Return a custom allocator implementation.
  32. allocator_type get_allocator() const noexcept
  33. {
  34. return my_allocator();
  35. }
  36. void operator()() { ... }
  37. };
  38. In more complex cases, the `associated_allocator` template may be partially
  39. specialised directly:
  40. namespace boost { namespace asio {
  41. template <typename Allocator>
  42. struct associated_allocator<my_handler, Allocator>
  43. {
  44. // Custom implementation of Allocator type requirements.
  45. typedef my_allocator type;
  46. // Return a custom allocator implementation.
  47. static type get(const my_handler&,
  48. const Allocator& a = Allocator()) noexcept
  49. {
  50. return my_allocator();
  51. }
  52. };
  53. } } // namespace boost::asio
  54. The implementation guarantees that the deallocation will occur before the
  55. associated handler is invoked, which means the memory is ready to be reused for
  56. any new asynchronous operations started by the handler.
  57. The custom memory allocation functions may be called from any user-created
  58. thread that is calling a library function. The implementation guarantees that,
  59. for the asynchronous operations included the library, the implementation will
  60. not make concurrent calls to the memory allocation functions for that handler.
  61. The implementation will insert appropriate memory barriers to ensure correct
  62. memory visibility should allocation functions need to be called from different
  63. threads.
  64. [heading See Also]
  65. [link boost_asio.reference.associated_allocator associated_allocator],
  66. [link boost_asio.reference.get_associated_allocator get_associated_allocator],
  67. [link boost_asio.examples.cpp03_examples.allocation custom memory allocation example (C++03)],
  68. [link boost_asio.examples.cpp11_examples.allocation custom memory allocation example (C++11)].
  69. [endsect]