mySQL 5.0.11 sources for tomato
[tomato.git] / release / src / router / mysql / server-tools / instance-manager / manager.cc
blob33f786d7bcfb49fb4efab72d68d6d05360353005
1 /* Copyright (c) 2003-2007 MySQL AB
3 This program is free software; you can redistribute it and/or modify
4 it under the terms of the GNU General Public License as published by
5 the Free Software Foundation; version 2 of the License.
7 This program is distributed in the hope that it will be useful,
8 but WITHOUT ANY WARRANTY; without even the implied warranty of
9 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 GNU General Public License for more details.
12 You should have received a copy of the GNU General Public License
13 along with this program; if not, write to the Free Software
14 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA */
16 #include "manager.h"
18 #include <my_global.h>
19 #include <m_string.h>
20 #include <my_sys.h>
21 #include <thr_alarm.h>
23 #include <signal.h>
24 #ifndef __WIN__
25 #include <sys/wait.h>
26 #endif
28 #include "exit_codes.h"
29 #include "guardian.h"
30 #include "instance_map.h"
31 #include "listener.h"
32 #include "mysql_manager_error.h"
33 #include "mysqld_error.h"
34 #include "log.h"
35 #include "options.h"
36 #include "priv.h"
37 #include "thread_registry.h"
38 #include "user_map.h"
41 /**********************************************************************
42 {{{ Platform-specific implementation.
43 **********************************************************************/
45 #ifndef __WIN__
46 void set_signals(sigset_t *mask)
48 /* block signals */
49 sigemptyset(mask);
50 sigaddset(mask, SIGINT);
51 sigaddset(mask, SIGTERM);
52 sigaddset(mask, SIGPIPE);
53 sigaddset(mask, SIGHUP);
54 signal(SIGPIPE, SIG_IGN);
57 We want this signal to be blocked in all theads but the signal
58 one. It is needed for the thr_alarm subsystem to work.
60 sigaddset(mask,THR_SERVER_ALARM);
62 /* all new threads will inherite this signal mask */
63 pthread_sigmask(SIG_BLOCK, mask, NULL);
66 In our case the signal thread also implements functions of alarm thread.
67 Here we init alarm thread functionality. We suppose that we won't have
68 more then 10 alarms at the same time.
70 init_thr_alarm(10);
72 #else
74 bool have_signal;
76 void onsignal(int signo)
78 have_signal= TRUE;
81 void set_signals(sigset_t *set)
83 signal(SIGINT, onsignal);
84 signal(SIGTERM, onsignal);
85 have_signal= FALSE;
88 int my_sigwait(const sigset_t *set, int *sig)
90 while (!have_signal)
92 Sleep(100);
94 return 0;
97 #endif
99 /**********************************************************************
101 **********************************************************************/
104 /**********************************************************************
105 {{{ Implementation of checking the actual thread model.
106 ***********************************************************************/
108 namespace { /* no-indent */
110 class ThreadModelChecker: public Thread
112 public:
113 ThreadModelChecker()
114 :main_pid(getpid())
117 public:
118 inline bool is_linux_threads() const
120 return linux_threads;
123 protected:
124 virtual void run()
126 linux_threads= main_pid != getpid();
129 private:
130 pid_t main_pid;
131 bool linux_threads;
134 bool check_if_linux_threads(bool *linux_threads)
136 ThreadModelChecker checker;
138 if (checker.start() || checker.join())
139 return TRUE;
141 *linux_threads= checker.is_linux_threads();
143 return FALSE;
148 /**********************************************************************
150 ***********************************************************************/
153 /**********************************************************************
154 Manager implementation
155 ***********************************************************************/
157 Guardian *Manager::p_guardian;
158 Instance_map *Manager::p_instance_map;
159 Thread_registry *Manager::p_thread_registry;
160 User_map *Manager::p_user_map;
162 #ifndef __WIN__
163 bool Manager::linux_threads;
164 #endif // __WIN__
168 Request shutdown of guardian and threads registered in Thread_registry.
170 SYNOPSIS
171 stop_all_threads()
174 void Manager::stop_all_threads()
177 Let Guardian thread know that it should break it's processing cycle,
178 once it wakes up.
180 p_guardian->request_shutdown();
182 /* Stop all threads. */
183 p_thread_registry->deliver_shutdown();
185 /* Set error status in the thread registry. */
186 p_thread_registry->set_error_status();
191 Initialize user map and load password file.
193 SYNOPSIS
194 init_user_map()
196 RETURN
197 FALSE on success
198 TRUE on failure
201 bool Manager::init_user_map(User_map *user_map)
203 int err_code;
204 const char *err_msg;
206 if (user_map->init())
208 log_error("Manager: can not initialize user list: out of memory.");
209 return TRUE;
212 err_code= user_map->load(Options::Main::password_file_name, &err_msg);
214 if (!err_code)
215 return FALSE;
217 if (err_code == ERR_PASSWORD_FILE_DOES_NOT_EXIST &&
218 Options::Main::mysqld_safe_compatible)
221 The password file does not exist, but we are running in
222 mysqld_safe-compatible mode. Continue, but complain in log.
225 log_info("Warning: password file does not exist, "
226 "nobody will be able to connect to Instance Manager.");
228 return FALSE;
231 log_error("Manager: %s.", (const char *) err_msg);
233 return TRUE;
238 Main manager function.
240 SYNOPSIS
241 main()
243 DESCRIPTION
244 This is an entry point to the main instance manager process:
245 start listener thread, write pid file and enter into signal handling.
246 See also comments in mysqlmanager.cc to picture general Instance Manager
247 architecture.
249 RETURNS
250 main() returns exit status (exit code).
253 int Manager::main()
255 bool shutdown_complete= FALSE;
256 pid_t manager_pid= getpid();
258 log_info("Manager: initializing...");
260 #ifndef __WIN__
261 if (check_if_linux_threads(&linux_threads))
263 log_error("Manager: can not determine thread model.");
264 return 1;
267 log_info("Manager: detected threads model: %s.",
268 (const char *) (linux_threads ? "LINUX threads" : "POSIX threads"));
269 #endif // __WIN__
272 All objects created in the Manager object live as long as thread_registry
273 lives, and thread_registry is alive until there are working threads.
275 There are two main purposes of the Thread Registry:
276 1. Interrupt blocking I/O and signal condition variables in case of
277 shutdown;
278 2. Wait for detached threads before shutting down the main thread.
280 NOTE:
281 1. Handling shutdown can be done in more elegant manner by introducing
282 Event (or Condition) object with support of logical operations.
283 2. Using Thread Registry to wait for detached threads is definitely not
284 the best way, because when Thread Registry unregisters an thread, the
285 thread is still alive. Accurate way to wait for threads to stop is
286 not using detached threads and join all threads before shutdown.
289 Thread_registry thread_registry;
290 User_map user_map;
291 Instance_map instance_map;
292 Guardian guardian(&thread_registry, &instance_map);
294 Listener listener(&thread_registry, &user_map);
296 p_instance_map= &instance_map;
297 p_guardian= &guardian;
298 p_thread_registry= &thread_registry;
299 p_user_map= &user_map;
301 /* Initialize instance map. */
303 if (instance_map.init())
305 log_error("Manager: can not initialize instance list: out of memory.");
306 return 1;
309 /* Initialize user db. */
311 if (init_user_map(&user_map))
312 return 1; /* logging has been already done. */
314 /* Write Instance Manager pid file. */
316 if (create_pid_file(Options::Main::pid_file_name, manager_pid))
317 return 1; /* necessary logging has been already done. */
319 log_info("Manager: pid file (%s) created.",
320 (const char *) Options::Main::pid_file_name);
323 Initialize signals and alarm-infrastructure.
325 NOTE: To work nicely with LinuxThreads, the signal thread is the first
326 thread in the process.
328 NOTE: After init_thr_alarm() call it's possible to call thr_alarm()
329 (from different threads), that results in sending ALARM signal to the
330 alarm thread (which can be the main thread). That signal can interrupt
331 blocking calls. In other words, a blocking call can be interrupted in
332 the main thread after init_thr_alarm().
335 sigset_t mask;
336 set_signals(&mask);
339 Create the guardian thread. The newly started thread will block until
340 we actually load instances.
342 NOTE: Guardian should be shutdown first. Only then all other threads
343 can be stopped. This should be done in this order because the guardian
344 is responsible for shutting down all the guarded instances, and this
345 is a long operation.
347 NOTE: Guardian uses thr_alarm() when detects the current state of an
348 instance (is_running()), but this does not interfere with
349 flush_instances() call later in the code, because until
350 flush_instances() completes in the main thread, Guardian thread is not
351 permitted to process instances. And before flush_instances() has
352 completed, there are no instances to guard.
355 if (guardian.start(Thread::DETACHED))
357 log_error("Manager: can not start Guardian thread.");
358 goto err;
361 /* Load instances. */
363 if (Manager::flush_instances())
365 log_error("Manager: can not init instances repository.");
366 stop_all_threads();
367 goto err;
370 /* Initialize the Listener. */
372 if (listener.start(Thread::DETACHED))
374 log_error("Manager: can not start Listener thread.");
375 stop_all_threads();
376 goto err;
380 After the list of guarded instances have been initialized,
381 Guardian should start them.
384 guardian.ping();
386 /* Main loop. */
388 log_info("Manager: started.");
390 while (!shutdown_complete)
392 int signo;
393 int status= 0;
395 if ((status= my_sigwait(&mask, &signo)) != 0)
397 log_error("Manager: sigwait() failed");
398 stop_all_threads();
399 goto err;
403 The general idea in this loop is the following:
404 - we are waiting for SIGINT, SIGTERM -- signals that mean we should
405 shutdown;
406 - as shutdown signal is caught, we stop Guardian thread (by calling
407 Guardian::request_shutdown());
408 - as Guardian is stopped, it sends SIGTERM to this thread
409 (by calling Thread_registry::request_shutdown()), so that the
410 my_sigwait() above returns;
411 - as we catch the second SIGTERM, we send signals to all threads
412 registered in Thread_registry (by calling
413 Thread_registry::deliver_shutdown()) and waiting for threads to stop;
416 #ifndef __WIN__
418 On some Darwin kernels SIGHUP is delivered along with most
419 signals. This is why we skip it's processing on these
420 platforms. For more details and test program see
421 Bug #14164 IM tests fail on MacOS X (powermacg5)
423 #ifdef IGNORE_SIGHUP_SIGQUIT
424 if (SIGHUP == signo)
425 continue;
426 #endif
427 if (THR_SERVER_ALARM == signo)
428 process_alarm(signo);
429 else
430 #endif
432 log_info("Manager: got shutdown signal.");
434 if (!guardian.is_stopped())
436 guardian.request_shutdown();
438 else
440 thread_registry.deliver_shutdown();
441 shutdown_complete= TRUE;
446 log_info("Manager: finished.");
448 err:
449 /* delete the pid file */
450 my_delete(Options::Main::pid_file_name, MYF(0));
452 #ifndef __WIN__
453 /* free alarm structures */
454 end_thr_alarm(1);
455 #endif
457 return thread_registry.get_error_status() ? 1 : 0;
462 Re-read instance configuration file.
464 SYNOPSIS
465 flush_instances()
467 DESCRIPTION
468 This function will:
469 - clear the current list of instances. This removes both
470 running and stopped instances.
471 - load a new instance configuration from the file.
472 - pass on the new map to the guardian thread: it will start
473 all instances that are marked `guarded' and not yet started.
475 Note, as the check whether an instance is started is currently
476 very simple (returns TRUE if there is a MySQL server running
477 at the given port), this function has some peculiar
478 side-effects:
479 * if the port number of a running instance was changed, the
480 old instance is forgotten, even if it was running. The new
481 instance will be started at the new port.
482 * if the configuration was changed in a way that two
483 instances swapped their port numbers, the guardian thread
484 will not notice that and simply report that both instances
485 are configured successfully and running.
487 In order to avoid such side effects one should never call
488 FLUSH INSTANCES without prior stop of all running instances.
490 RETURN
491 0 On success
492 ER_OUT_OF_RESOURCES Not enough resources to complete the operation
493 ER_THERE_IS_ACTIVE_INSTACE If there is an active instance
496 int Manager::flush_instances()
498 p_instance_map->lock();
500 if (p_instance_map->is_there_active_instance())
502 p_instance_map->unlock();
503 return ER_THERE_IS_ACTIVE_INSTACE;
506 if (p_instance_map->reset())
508 p_instance_map->unlock();
509 return ER_OUT_OF_RESOURCES;
512 if (p_instance_map->load())
514 p_instance_map->unlock();
516 /* Don't init guardian if we failed to load instances. */
517 return ER_OUT_OF_RESOURCES;
520 get_guardian()->init();
521 get_guardian()->ping();
523 p_instance_map->unlock();
525 return 0;