dispatcher.h 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778
  1. // Copyright (c) 2022 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #ifndef BASE_ALLOCATOR_DISPATCHER_DISPATCHER_H_
  5. #define BASE_ALLOCATOR_DISPATCHER_DISPATCHER_H_
  6. #include "base/allocator/dispatcher/internal/dispatcher_internal.h"
  7. #include "base/base_export.h"
  8. #include <memory>
  9. namespace base::allocator::dispatcher {
  10. void BASE_EXPORT InstallStandardAllocatorHooks();
  11. void BASE_EXPORT RemoveStandardAllocatorHooksForTesting();
  12. namespace internal {
  13. struct DispatchData;
  14. }
  15. // Dispatcher serves as the top level instance for managing the dispatch
  16. // mechanism. The class instance manages connections to the various memory
  17. // subsystems such as PartitionAlloc. To keep the public interface as lean as
  18. // possible it uses a pimpl pattern.
  19. class BASE_EXPORT Dispatcher {
  20. public:
  21. static Dispatcher& GetInstance();
  22. Dispatcher();
  23. // Initialize the dispatch mechanism with the given tuple of observers. The
  24. // observers must be valid (it is only DCHECKed internally at initialization,
  25. // but not verified further)
  26. // If Initialize is called multiple times, the first one wins. All later
  27. // invocations are silently ignored. Initialization is protected from
  28. // concurrent invocations. In case of concurrent accesses, the first one to
  29. // get the lock wins.
  30. // The dispatcher invokes following functions on the observers:
  31. // void OnAllocation(void* address,
  32. // size_t size,
  33. // AllocationSubsystem sub_system,
  34. // const char* type_name);
  35. // void OnFree(void* address);
  36. //
  37. // Note: The dispatcher mechanism does NOT bring systematic protection against
  38. // recursive invocations. That is, observers which allocate memory on the
  39. // heap, i.e. through dynamically allocated containers or by using the
  40. // CHECK-macro, are responsible to break these recursions!
  41. template <typename... ObserverTypes>
  42. void Initialize(const std::tuple<ObserverTypes...>& observers) {
  43. // Get the hooks for running these observers and pass them to further
  44. // initialization
  45. Initialize(internal::GetNotificationHooks(observers));
  46. }
  47. // The following functions provide an interface to setup and tear down the
  48. // dispatcher when testing. This must NOT be used from production code since
  49. // the hooks cannot be removed reliably under all circumstances.
  50. template <typename ObserverType>
  51. void InitializeForTesting(ObserverType* observer) {
  52. Initialize(std::make_tuple(observer));
  53. }
  54. void ResetForTesting();
  55. private:
  56. // structure and pointer to the private implementation.
  57. struct Impl;
  58. std::unique_ptr<Impl> const impl_;
  59. ~Dispatcher();
  60. void Initialize(const internal::DispatchData& dispatch_data);
  61. };
  62. } // namespace base::allocator::dispatcher
  63. #endif // BASE_ALLOCATOR_DISPATCHER_DISPATCHER_H_