Automatic Differentiation
 
Loading...
Searching...
No Matches
init_chainablestack.hpp
Go to the documentation of this file.
1#ifndef STAN_MATH_REV_CORE_INIT_CHAINABLESTACK_HPP
2#define STAN_MATH_REV_CORE_INIT_CHAINABLESTACK_HPP
3
5
6#include <tbb/task_scheduler_observer.h>
7
8#include <mutex>
9#include <unordered_map>
10#include <utility>
11#include <thread>
12#include <tuple>
13
14#ifdef __APPLE__
15#include <pthread.h>
16#include <sys/qos.h>
17#endif
18
19namespace stan {
20namespace math {
21
36class ad_tape_observer final : public tbb::task_scheduler_observer {
37 using stack_ptr = std::unique_ptr<ChainableStack>;
38 using ad_map = std::unordered_map<std::thread::id, stack_ptr>;
39
40 public:
41 ad_tape_observer() : tbb::task_scheduler_observer(), thread_tape_map_() {
42 on_scheduler_entry(true); // register current process
43 observe(true); // activates the observer
44 }
45
46 ~ad_tape_observer() { observe(false); }
47
48 void on_scheduler_entry(bool worker) {
49#ifdef __APPLE__
50#if defined(__arm64__) || defined(__aarch64__)
51 // Set thread QoS to USER_INITIATED so macOS prefers scheduling
52 // TBB worker threads on performance cores rather than efficiency cores.
53 pthread_set_qos_class_self_np(QOS_CLASS_USER_INITIATED, 0);
54#endif
55#endif
56 std::lock_guard<std::mutex> thread_tape_map_lock(thread_tape_map_mutex_);
57 const std::thread::id thread_id = std::this_thread::get_id();
58 if (thread_tape_map_.find(thread_id) == thread_tape_map_.end()) {
59 ad_map::iterator insert_elem;
60 bool status = false;
61 std::tie(insert_elem, status)
62 = thread_tape_map_.emplace(ad_map::value_type{thread_id, nullptr});
63 insert_elem->second = std::make_unique<ChainableStack>();
64 }
65 }
66
67 void on_scheduler_exit(bool worker) {
68 std::lock_guard<std::mutex> thread_tape_map_lock(thread_tape_map_mutex_);
69 auto elem = thread_tape_map_.find(std::this_thread::get_id());
70 if (elem != thread_tape_map_.end()) {
71 thread_tape_map_.erase(elem);
72 }
73 }
74
75 private:
78};
79
80namespace {
81
82ad_tape_observer global_observer;
83
84} // namespace
85} // namespace math
86} // namespace stan
87
88#endif
std::unordered_map< std::thread::id, stack_ptr > ad_map
std::unique_ptr< ChainableStack > stack_ptr
TBB observer object which is a callback hook called whenever the TBB scheduler adds a new thread to t...
The lgamma implementation in stan-math is based on either the reentrant safe lgamma_r implementation ...