MySQL  8.0.27
Source Code Documentation
mysqld_thd_manager.h
Go to the documentation of this file.
1 /* Copyright (c) 2013, 2021, Oracle and/or its affiliates.
2 
3  This program is free software; you can redistribute it and/or modify
4  it under the terms of the GNU General Public License, version 2.0,
5  as published by the Free Software Foundation.
6 
7  This program is also distributed with certain software (including
8  but not limited to OpenSSL) that is licensed under separate terms,
9  as designated in a particular file or component or in included license
10  documentation. The authors of MySQL hereby grant you an additional
11  permission to link the program and your derivative works with the
12  separately licensed software that they have included with MySQL.
13 
14  This program is distributed in the hope that it will be useful,
15  but WITHOUT ANY WARRANTY; without even the implied warranty of
16  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17  GNU General Public License, version 2.0, for more details.
18 
19  You should have received a copy of the GNU General Public License
20  along with this program; if not, write to the Free Software
21  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
22 
23 #ifndef MYSQLD_THD_MANAGER_INCLUDED
24 #define MYSQLD_THD_MANAGER_INCLUDED
25 
26 #include <assert.h>
27 #include <stddef.h>
28 #include <sys/types.h>
29 #include <atomic>
30 
31 #include "my_inttypes.h"
32 #include "my_thread_local.h" // my_thread_id
35 #include "prealloced_array.h"
36 
37 class THD;
38 
41 
42 /**
43  Base class to perform actions on all thds in the thd list.
44  Users of do_for_all_thd() need to subclass this and override operator().
45 
46  @note THD can be in the disposal state. Accessing resources freed in disposal
47  state is not safe. Before accessing any such resources in operator()
48  please check THD state.
49 */
50 
51 class Do_THD_Impl {
52  public:
53  virtual ~Do_THD_Impl() = default;
54  virtual void operator()(THD *) = 0;
55 };
56 
57 /**
58  Base class to find specific thd from the thd list.
59  Users of find_thd() need to subclass this and override operator()
60  to provide implementation to find thd from thd list.
61 */
62 
64  public:
65  virtual ~Find_THD_Impl() = default;
66  /**
67  Override this operator to provide implementation to find specific thd.
68 
69  @param thd THD of one element in global thread list
70 
71  @returns bool
72  @retval true for matching thd
73  false otherwise
74  */
75  virtual bool operator()(THD *thd) = 0;
76 };
77 
78 /**
79  Callback function used by kill_one_thread and timer_notify functions
80  to find "thd" based on the thread id.
81 */
83  public:
85  bool operator()(THD *thd) override;
86 
88 };
89 
90 /**
91  This class encapsulates THD instance, controls access to the actual THD.
92  It also ensures that THD::LOCK_thd_data mutex is acquired at instantiation and
93  released at destruction.
94 */
95 class THD_ptr {
96  public:
97  /**
98  Default class constructor.
99  */
100  THD_ptr() = default;
101  /**
102  Constructor assigns THD instance to manage and acquires THD::LOCK_thd_data
103  mutex.
104  @param thd THD instance.
105  */
106  explicit THD_ptr(THD *thd);
107  /**
108  Delete copy constructor, THD_ptr copy is not allowed.
109  */
110  THD_ptr(THD_ptr const &) = delete;
111  /**
112  Move constructor.
113  @param thd_ptr THD_ptr instance to collect underlying THD instance.
114  */
115  THD_ptr(THD_ptr &&thd_ptr);
116 
117  /**
118  Destructor to release underlying THD instance's control and release mutex
119  THD::LOCK_thd_data.
120  */
121  ~THD_ptr() { release(); }
122  /**
123  Release underlying THD instance's control and release THD::LOCK_thd_data.
124  @returns underlying THD instance.
125  */
126  THD *release();
127 
128  /**
129  Delete copy operator, THD_ptr copy is not allowed.
130  */
131  THD_ptr &operator=(THD_ptr const &) = delete;
132  /**
133  Move semantics assignment operator.
134  @param thd_ptr THD_ptr instance to collect underlying THD instance.
135  */
136  THD_ptr &operator=(THD_ptr &&thd_ptr);
137 
138  /**
139  Access underlying THD instance.
140  returns pointer to underlying THD instance.
141  */
142  THD *get() { return m_underlying; }
143  /**
144  Access underlying THD instance.
145  returns pointer to underlying THD instance.
146  */
147  THD *operator->() { return m_underlying; }
148  /**
149  Access underlying THD instance.
150  returns reference to underlying THD instance.
151  */
152  THD &operator*() { return *m_underlying; }
153 
154  /**
155  Check if there is an underlying THD instance.
156  */
157  operator bool() const { return m_underlying != nullptr; }
158 
159  /**
160  Compare underlying THD pointer value with the "nullptr".
161  @returns true if underlying THD pointer value equals "nullptr".
162  */
163  bool operator==(std::nullptr_t) const { return m_underlying == nullptr; }
164  /**
165  Compare this instance with other THD_ptr instance.
166  @param thd_ptr Other THD_ptr instance for comparison.
167  @returns true if this instance equals other THD_ptr instance.
168  */
169  bool operator==(THD const *thd_ptr) const { return m_underlying == thd_ptr; }
170  /**
171  Compare underlying THD pointer value with the "nullptr".
172  @returns true if underlying THD pointer value *not* equals nullptr.
173  */
174  bool operator!=(std::nullptr_t) const { return m_underlying != nullptr; }
175  /**
176  Compare this instance with other THD_ptr instance.
177  @param thd_ptr Other THD_ptr instance for comparison.
178  @returns true if this instance differs from other THD_ptr instance.
179  */
180  bool operator!=(THD const *thd_ptr) const { return m_underlying != thd_ptr; }
181 
182  private:
183  // Underlying THD instance to manage.
184  THD *m_underlying{nullptr};
185 };
186 
187 /**
188  This class maintains THD object of all registered threads.
189  It provides interface to perform functions such as find, count,
190  perform some action for each THD object in the list.
191 
192  It also provide mutators for inserting, and removing an element:
193  add_thd() inserts a THD into the set, and increments the counter.
194  remove_thd() removes a THD from the set, and decrements the counter.
195  Method remove_thd() also broadcasts COND_thd_list.
196 */
197 
199  public:
200  /**
201  Value for thread_id reserved for THDs which does not have an
202  assigned value yet. get_new_thread_id() will never return this
203  value.
204  */
206 
207  /**
208  Retrieves singleton instance
209  */
211  assert(thd_manager != nullptr);
212  return thd_manager;
213  }
214 
215  /**
216  Initializes the thd manager.
217  Must be called before get_instance() can be used.
218 
219  @return true if initialization failed, false otherwise.
220  */
221  static bool create_instance();
222 
223  /**
224  Destroys the singleton instance.
225  */
226  static void destroy_instance();
227 
228  /**
229  Internally used to bypass code.
230  It enables unit test scripts to create dummy THD object for testing.
231  */
232  void set_unit_test() { unit_test = true; }
233 
234  /**
235  Adds THD to global THD list.
236 
237  @param thd THD object
238  */
239  void add_thd(THD *thd);
240 
241  /**
242  Removes THD from global THD list.
243 
244  @param thd THD object
245  */
246  void remove_thd(THD *thd);
247 
248  /**
249  Retrieves thread running statistic variable.
250  @return int Returns the total number of threads currently running
251  */
253 
254  /**
255  Increments thread running statistic variable.
256  */
258 
259  /**
260  Decrements thread running statistic variable.
261  */
263 
264  /**
265  Retrieves thread created statistic variable.
266  @return ulonglong Returns the total number of threads created
267  after server start
268  */
270 
271  /**
272  Increments thread created statistic variable.
273  */
275 
276  /**
277  Returns an unused thread id.
278  */
280 
281  /**
282  Releases a thread id so that it can be reused.
283  Note that this is done automatically by remove_thd().
284  */
286 
287  /**
288  Retrieves thread id counter value.
289  @return my_thread_id Returns the thread id counter value
290  @note This is a dirty read.
291  */
293 
294  /**
295  Sets thread id counter value. Only used in testing for now.
296  @param new_id The next ID to hand out (if it's unused).
297  */
299 
300  /**
301  Retrieves total number of items in global THD lists (all partitions).
302  @return uint Returns the count of items in global THD lists.
303  */
305 
306  /**
307  Waits until all THDs are removed from global THD lists (all partitions).
308  In other words, get_thd_count() to become zero.
309  */
310  void wait_till_no_thd();
311 
312  /**
313  This function calls func() for all THDs in every thd list partition
314  after taking local copy of the THD list partition. It acquires
315  LOCK_thd_remove to prevent removal of the THD.
316  @param func Object of class which overrides operator()
317  */
318  void do_for_all_thd_copy(Do_THD_Impl *func);
319 
320  /**
321  This function calls func() for all THDs in all THD list partitions.
322  @param func Object of class which overrides operator()
323  @note One list partition is unlocked before the next partition is locked.
324  */
325  void do_for_all_thd(Do_THD_Impl *func);
326 
327  /**
328  Returns a THD_ptr containing first THD for which operator() returns true.
329 
330  @param func Object of class which overrides operator()
331  @return THD_ptr
332  @retval THD_ptr{THD*} When matching THD is found.
333  @retval THD_ptr{nullptr} When THD is *not* found.
334  */
336 
338 
339  // Declared static as it is referenced in handle_fatal_signal()
340  static std::atomic<uint> atomic_global_thd_count;
341 
342  // Number of THD list partitions.
343  static const int NUM_PARTITIONS = 8;
344 
345  private:
348 
349  // Singleton instance.
351 
352  // Array of current THDs. Protected by LOCK_thd_list.
355 
356  // Array of thread ID in current use. Protected by LOCK_thread_ids.
359 
361 
362  // Mutexes that guard thd_list partitions
364  // Mutexes used to guard removal of elements from thd_list partitions.
366  // Mutex protecting thread_ids
368 
369  // Count of active threads which are running queries in the system.
370  std::atomic<int> atomic_num_thread_running;
371 
372  // Cumulative number of threads created by mysqld daemon.
373  std::atomic<ulonglong> atomic_thread_created;
374 
375  // Counter to assign thread id.
377 
378  // Used during unit test to bypass creating real THD object.
379  bool unit_test;
380 
381  friend void thd_lock_thread_count();
382  friend void thd_unlock_thread_count();
383 };
384 
385 #endif /* MYSQLD_INCLUDED */
Base class to perform actions on all thds in the thd list.
Definition: mysqld_thd_manager.h:51
virtual ~Do_THD_Impl()=default
virtual void operator()(THD *)=0
Base class to find specific thd from the thd list.
Definition: mysqld_thd_manager.h:63
virtual ~Find_THD_Impl()=default
virtual bool operator()(THD *thd)=0
Override this operator to provide implementation to find specific thd.
Callback function used by kill_one_thread and timer_notify functions to find "thd" based on the threa...
Definition: mysqld_thd_manager.h:82
bool operator()(THD *thd) override
Override this operator to provide implementation to find specific thd.
Definition: mysqld_thd_manager.cc:59
Find_thd_with_id(my_thread_id value)
Definition: mysqld_thd_manager.h:84
const my_thread_id m_thread_id
Definition: mysqld_thd_manager.h:87
This class maintains THD object of all registered threads.
Definition: mysqld_thd_manager.h:198
std::atomic< int > atomic_num_thread_running
Definition: mysqld_thd_manager.h:370
~Global_THD_manager()
Definition: mysqld_thd_manager.cc:189
void add_thd(THD *thd)
Adds THD to global THD list.
Definition: mysqld_thd_manager.cc:216
mysql_mutex_t LOCK_thd_remove[NUM_PARTITIONS]
Definition: mysqld_thd_manager.h:365
static std::atomic< uint > atomic_global_thd_count
Definition: mysqld_thd_manager.h:340
static Global_THD_manager * thd_manager
Definition: mysqld_thd_manager.h:350
void inc_thread_running()
Increments thread running statistic variable.
Definition: mysqld_thd_manager.h:257
void do_for_all_thd_copy(Do_THD_Impl *func)
This function calls func() for all THDs in every thd list partition after taking local copy of the TH...
Definition: mysqld_thd_manager.cc:286
my_thread_id thread_id_counter
Definition: mysqld_thd_manager.h:376
Prealloced_array< THD *, 60 > THD_array
Definition: mysqld_thd_manager.h:353
friend void thd_lock_thread_count()
Definition: mysqld_thd_manager.cc:353
mysql_mutex_t LOCK_thd_list[NUM_PARTITIONS]
Definition: mysqld_thd_manager.h:363
my_thread_id get_thread_id() const
Retrieves thread id counter value.
Definition: mysqld_thd_manager.h:292
void do_for_all_thd(Do_THD_Impl *func)
This function calls func() for all THDs in all THD list partitions.
Definition: mysqld_thd_manager.cc:309
void set_unit_test()
Internally used to bypass code.
Definition: mysqld_thd_manager.h:232
bool unit_test
Definition: mysqld_thd_manager.h:379
static Global_THD_manager * get_instance()
Retrieves singleton instance.
Definition: mysqld_thd_manager.h:210
void release_thread_id(my_thread_id thread_id)
Releases a thread id so that it can be reused.
Definition: mysqld_thd_manager.cc:261
static const my_thread_id reserved_thread_id
Value for thread_id reserved for THDs which does not have an assigned value yet.
Definition: mysqld_thd_manager.h:205
int get_num_thread_running() const
Retrieves thread running statistic variable.
Definition: mysqld_thd_manager.h:252
Thread_id_array thread_ids
Definition: mysqld_thd_manager.h:358
void dec_thread_running()
Decrements thread running statistic variable.
Definition: mysqld_thd_manager.h:262
my_thread_id get_new_thread_id()
Returns an unused thread id.
Definition: mysqld_thd_manager.cc:252
static void destroy_instance()
Destroys the singleton instance.
Definition: mysqld_thd_manager.cc:211
THD_array thd_list[NUM_PARTITIONS]
Definition: mysqld_thd_manager.h:354
void set_thread_id_counter(my_thread_id new_id)
Sets thread id counter value.
Definition: mysqld_thd_manager.cc:270
std::atomic< ulonglong > atomic_thread_created
Definition: mysqld_thd_manager.h:373
ulonglong get_num_thread_created() const
Retrieves thread created statistic variable.
Definition: mysqld_thd_manager.h:269
void wait_till_no_thd()
Waits until all THDs are removed from global THD lists (all partitions).
Definition: mysqld_thd_manager.cc:276
friend void thd_unlock_thread_count()
Definition: mysqld_thd_manager.cc:358
void remove_thd(THD *thd)
Removes THD from global THD list.
Definition: mysqld_thd_manager.cc:230
Global_THD_manager()
Definition: mysqld_thd_manager.cc:149
mysql_mutex_t LOCK_thread_ids
Definition: mysqld_thd_manager.h:367
static uint get_thd_count()
Retrieves total number of items in global THD lists (all partitions).
Definition: mysqld_thd_manager.h:304
void inc_thread_created()
Increments thread created statistic variable.
Definition: mysqld_thd_manager.h:274
mysql_cond_t COND_thd_list[NUM_PARTITIONS]
Definition: mysqld_thd_manager.h:360
Prealloced_array< my_thread_id, 1000 > Thread_id_array
Definition: mysqld_thd_manager.h:357
static bool create_instance()
Initializes the thd manager.
Definition: mysqld_thd_manager.cc:205
static const int NUM_PARTITIONS
Definition: mysqld_thd_manager.h:343
THD_ptr find_thd(Find_THD_Impl *func)
Returns a THD_ptr containing first THD for which operator() returns true.
Definition: mysqld_thd_manager.cc:317
This class encapsulates THD instance, controls access to the actual THD.
Definition: mysqld_thd_manager.h:95
bool operator==(std::nullptr_t) const
Compare underlying THD pointer value with the "nullptr".
Definition: mysqld_thd_manager.h:163
THD * operator->()
Access underlying THD instance.
Definition: mysqld_thd_manager.h:147
~THD_ptr()
Destructor to release underlying THD instance's control and release mutex THD::LOCK_thd_data.
Definition: mysqld_thd_manager.h:121
THD_ptr(THD_ptr const &)=delete
Delete copy constructor, THD_ptr copy is not allowed.
bool operator!=(std::nullptr_t) const
Compare underlying THD pointer value with the "nullptr".
Definition: mysqld_thd_manager.h:174
THD * m_underlying
Definition: mysqld_thd_manager.h:184
THD & operator*()
Access underlying THD instance.
Definition: mysqld_thd_manager.h:152
THD_ptr & operator=(THD_ptr const &)=delete
Delete copy operator, THD_ptr copy is not allowed.
THD_ptr()=default
Default class constructor.
bool operator!=(THD const *thd_ptr) const
Compare this instance with other THD_ptr instance.
Definition: mysqld_thd_manager.h:180
THD * release()
Release underlying THD instance's control and release THD::LOCK_thd_data.
Definition: mysqld_thd_manager.cc:118
THD * get()
Access underlying THD instance.
Definition: mysqld_thd_manager.h:142
bool operator==(THD const *thd_ptr) const
Compare this instance with other THD_ptr instance.
Definition: mysqld_thd_manager.h:169
For each client connection we create a separate thread with THD serving as a thread/connection descri...
Definition: sql_class.h:821
Some integer typedefs for easier portability.
unsigned long long int ulonglong
Definition: my_inttypes.h:55
static my_thread_id thread_id
Definition: my_thr_init.cc:62
uint32 my_thread_id
Definition: my_thread_local.h:33
Instrumentation helpers for conditions.
ABI for instrumented mutexes.
void thd_lock_thread_count()
Definition: mysqld_thd_manager.cc:353
void thd_unlock_thread_count()
Definition: mysqld_thd_manager.cc:358
const string value("\"Value\"")
An instrumented cond structure.
Definition: mysql_cond_bits.h:49
An instrumented mutex structure.
Definition: mysql_mutex_bits.h:49
unsigned int uint
Definition: uca-dump.cc:29
uint32_t new_id()
Create a new (hopefully unique) ID.
Definition: xcom_base.cc:1766