2 Bacula® - The Network Backup Solution
4 Copyright (C) 2000-2007 Free Software Foundation Europe e.V.
6 The main author of Bacula is Kern Sibbald, with contributions from
7 many others, a complete list can be found in the file AUTHORS.
8 This program is Free Software; you can redistribute it and/or
9 modify it under the terms of version two of the GNU General Public
10 License as published by the Free Software Foundation and included
13 This program is distributed in the hope that it will be useful, but
14 WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
23 Bacula® is a registered trademark of John Walker.
24 The licensor of Bacula is the Free Software Foundation Europe
25 (FSFE), Fiduciary Program, Sumatrastrasse 25, 8006 Zürich,
26 Switzerland, email:ftf@fsfeurope.org.
30 * Bacula Director daemon -- this is the main program
32 * Kern Sibbald, March MM
40 /* Forward referenced subroutines */
41 void terminate_dird(int sig);
42 static bool check_resources();
43 static bool check_catalog();
44 static void dir_sql_query(JCR *jcr, const char *cmd);
46 /* Exported subroutines */
47 extern "C" void reload_config(int sig);
48 extern void invalidate_schedules();
51 /* Imported subroutines */
52 JCR *wait_for_next_job(char *runjob);
53 void term_scheduler();
54 void term_ua_server();
55 void start_UA_server(dlist *addrs);
56 void init_job_server(int max_workers);
57 void term_job_server();
58 void store_jobtype(LEX *lc, RES_ITEM *item, int index, int pass);
59 void store_level(LEX *lc, RES_ITEM *item, int index, int pass);
60 void store_replace(LEX *lc, RES_ITEM *item, int index, int pass);
61 void init_device_resources();
63 static char *runjob = NULL;
64 static int background = 1;
65 static void init_reload(void);
67 /* Globals Exported */
68 DIRRES *director; /* Director resource */
71 char *configfile = NULL;
74 /* Globals Imported */
75 extern int r_first, r_last; /* first and last resources */
76 extern RES_TABLE resources[];
77 extern RES **res_head;
78 extern RES_ITEM job_items[];
81 extern "C" { // work around visual compiler mangling variables
88 #define CONFIG_FILE "bacula-dir.conf" /* default configuration file */
94 "\nVersion: %s (%s)\n\n"
95 "Usage: dird [-f -s] [-c config_file] [-d debug_level] [config_file]\n"
96 " -c <file> set configuration file to file\n"
97 " -d <nn> set debug level to <nn>\n"
98 " -dt print timestamp in debug output\n"
99 " -f run in foreground (for debugging)\n"
101 " -r <job> run <job> now\n"
103 " -t test - read configuration and exit\n"
105 " -v verbose user messages\n"
106 " -? print this message.\n"
107 "\n"), 2000, VERSION, BDATE);
113 /*********************************************************************
115 * Main Bacula Server program
118 #if defined(HAVE_WIN32)
119 /* For Win32 main() is in src/win32 code ... */
120 #define main BaculaMain
123 int main (int argc, char *argv[])
127 bool no_signals = false;
128 bool test_config = false;
132 start_heap = sbrk(0);
133 setlocale(LC_ALL, "");
134 bindtextdomain("bacula", LOCALEDIR);
135 textdomain("bacula");
138 my_name_is(argc, argv, "bacula-dir");
139 init_msg(NULL, NULL); /* initialize message handler */
141 daemon_start_time = time(NULL);
143 while ((ch = getopt(argc, argv, "c:d:fg:r:stu:v?")) != -1) {
145 case 'c': /* specify config file */
146 if (configfile != NULL) {
149 configfile = bstrdup(optarg);
152 case 'd': /* set debug level */
153 if (*optarg == 't') {
154 dbg_timestamp = true;
156 debug_level = atoi(optarg);
157 if (debug_level <= 0) {
161 Dmsg1(10, "Debug level = %d\n", debug_level);
164 case 'f': /* run in foreground */
168 case 'g': /* set group id */
172 case 'r': /* run job */
173 if (runjob != NULL) {
177 runjob = bstrdup(optarg);
181 case 's': /* turn off signals */
185 case 't': /* test config */
189 case 'u': /* set uid */
193 case 'v': /* verbose */
207 init_signals(terminate_dird);
211 if (configfile != NULL) {
214 configfile = bstrdup(*argv);
222 if (configfile == NULL) {
223 configfile = bstrdup(CONFIG_FILE);
226 parse_config(configfile);
228 if (init_crypto() != 0) {
229 Jmsg((JCR *)NULL, M_ERROR_TERM, 0, _("Cryptography library initialization failed.\n"));
232 if (!check_resources()) {
233 Jmsg((JCR *)NULL, M_ERROR_TERM, 0, _("Please correct configuration file: %s\n"), configfile);
236 if (!test_config) { /* we don't need to do this block in test mode */
239 init_stack_dump(); /* grab new pid */
242 /* Create pid must come after we are a daemon -- so we have our final pid */
243 create_pid_file(director->pid_directory, "bacula-dir", get_first_port_host_order(director->DIRaddrs));
244 read_state_file(director->working_directory, "bacula-dir", get_first_port_host_order(director->DIRaddrs));
247 drop(uid, gid); /* reduce privileges if requested */
249 if (!check_catalog()) {
250 Jmsg((JCR *)NULL, M_ERROR_TERM, 0, _("Please correct configuration file: %s\n"), configfile);
257 my_name_is(0, NULL, director->name()); /* set user defined name */
259 /* Plug database interface for library routines */
260 p_sql_query = (sql_query)dir_sql_query;
261 p_sql_escape = (sql_escape)db_escape_string;
263 FDConnectTimeout = (int)director->FDConnectTimeout;
264 SDConnectTimeout = (int)director->SDConnectTimeout;
267 #if !defined(HAVE_WIN32)
268 signal(SIGHUP, reload_config);
271 init_console_msg(working_directory);
273 init_python_interpreter(director->name(), director->scripts_directory,
276 set_thread_concurrency(director->MaxConcurrentJobs * 2 +
277 4 /* UA */ + 4 /* sched+watchdog+jobsvr+misc */);
279 Dmsg0(200, "Start UA server\n");
280 start_UA_server(director->DIRaddrs);
282 start_watchdog(); /* start network watchdog thread */
284 init_jcr_subsystem(); /* start JCR watchdogs etc. */
286 init_job_server(director->MaxConcurrentJobs);
288 // init_device_resources();
290 Dmsg0(200, "wait for next job\n");
291 /* Main loop -- call scheduler to get next job to run */
292 while ( (jcr = wait_for_next_job(runjob)) ) {
293 run_job(jcr); /* run job */
294 free_jcr(jcr); /* release jcr */
295 if (runjob) { /* command line, run a single job? */
296 break; /* yes, terminate */
306 * This allows the message handler to operate on the database
307 * by using a pointer to this function. The pointer is
308 * needed because the other daemons do not have access
309 * to the database. If the pointer is
310 * not defined (other daemons), then writing the database
313 static void dir_sql_query(JCR *jcr, const char *cmd)
315 if (!jcr || !jcr->db) {
318 db_sql_query(jcr->db, cmd, NULL, NULL);
321 /* Cleanup and then exit */
322 void terminate_dird(int sig)
324 static bool already_here = false;
326 if (already_here) { /* avoid recursive temination problems */
327 bmicrosleep(2, 0); /* yield */
332 generate_daemon_event(NULL, "Exit");
333 write_state_file(director->working_directory, "bacula-dir", get_first_port_host_order(director->DIRaddrs));
334 delete_pid_file(director->pid_directory, "bacula-dir", get_first_port_host_order(director->DIRaddrs));
340 if (configfile != NULL) {
343 if (debug_level > 5) {
344 print_memory_pool_stats();
346 free_config_resources();
348 term_msg(); /* terminate message handler */
350 close_memory_pool(); /* release free memory in pool */
355 struct RELOAD_TABLE {
360 static const int max_reloads = 32;
361 static RELOAD_TABLE reload_table[max_reloads];
363 static void init_reload(void)
365 for (int i=0; i < max_reloads; i++) {
366 reload_table[i].job_count = 0;
367 reload_table[i].res_table = NULL;
371 static void free_saved_resources(int table)
373 int num = r_last - r_first + 1;
374 RES **res_tab = reload_table[table].res_table;
376 Dmsg1(100, "res_tab for table %d already released.\n", table);
379 Dmsg1(100, "Freeing resources for table %d\n", table);
380 for (int j=0; j<num; j++) {
381 free_resource(res_tab[j], r_first + j);
384 reload_table[table].job_count = 0;
385 reload_table[table].res_table = NULL;
389 * Called here at the end of every job that was
390 * hooked decrementing the active job_count. When
391 * it goes to zero, no one is using the associated
392 * resource table, so free it.
394 static void reload_job_end_cb(JCR *jcr, void *ctx)
396 int reload_id = (int)((long int)ctx);
397 Dmsg3(100, "reload job_end JobId=%d table=%d cnt=%d\n", jcr->JobId,
398 reload_id, reload_table[reload_id].job_count);
401 if (--reload_table[reload_id].job_count <= 0) {
402 free_saved_resources(reload_id);
408 static int find_free_reload_table_entry()
411 for (int i=0; i < max_reloads; i++) {
412 if (reload_table[i].res_table == NULL) {
421 * If we get here, we have received a SIGHUP, which means to
422 * reread our configuration file.
424 * The algorithm used is as follows: we count how many jobs are
425 * running and mark the running jobs to make a callback on
426 * exiting. The old config is saved with the reload table
427 * id in a reload table. The new config file is read. Now, as
428 * each job exits, it calls back to the reload_job_end_cb(), which
429 * decrements the count of open jobs for the given reload table.
430 * When the count goes to zero, we release those resources.
431 * This allows us to have pointers into the resource table (from
432 * jobs), and once they exit and all the pointers are released, we
433 * release the old table. Note, if no new jobs are running since the
434 * last reload, then the old resources will be immediately release.
435 * A console is considered a job because it may have pointers to
436 * resources, but a SYSTEM job is not since it *should* not have any
437 * permanent pointers to jobs.
440 void reload_config(int sig)
442 static bool already_here = false;
443 #if !defined(HAVE_WIN32)
447 int njobs = 0; /* number of running jobs */
452 abort(); /* Oops, recursion -> die */
456 #if !defined(HAVE_WIN32)
458 sigaddset(&set, SIGHUP);
459 sigprocmask(SIG_BLOCK, &set, NULL);
465 table = find_free_reload_table_entry();
467 Jmsg(NULL, M_ERROR, 0, _("Too many open reload requests. Request ignored.\n"));
471 Dmsg1(100, "Reload_config njobs=%d\n", njobs);
472 reload_table[table].res_table = save_config_resources();
473 Dmsg1(100, "Saved old config in table %d\n", table);
475 ok = parse_config(configfile, 0, M_ERROR); /* no exit on error */
477 Dmsg0(100, "Reloaded config file\n");
478 if (!ok || !check_resources() || !check_catalog()) {
479 rtable = find_free_reload_table_entry(); /* save new, bad table */
481 Jmsg(NULL, M_ERROR, 0, _("Please correct configuration file: %s\n"), configfile);
482 Jmsg(NULL, M_ERROR_TERM, 0, _("Out of reload table entries. Giving up.\n"));
484 Jmsg(NULL, M_ERROR, 0, _("Please correct configuration file: %s\n"), configfile);
485 Jmsg(NULL, M_ERROR, 0, _("Resetting previous configuration.\n"));
487 reload_table[rtable].res_table = save_config_resources();
488 /* Now restore old resoure values */
489 int num = r_last - r_first + 1;
490 RES **res_tab = reload_table[table].res_table;
491 for (int i=0; i<num; i++) {
492 res_head[i] = res_tab[i];
494 table = rtable; /* release new, bad, saved table below */
496 invalidate_schedules();
498 * Hook all active jobs so that they release this table
501 if (jcr->JobType != JT_SYSTEM) {
502 reload_table[table].job_count++;
503 job_end_push(jcr, reload_job_end_cb, (void *)((long int)table));
511 set_working_directory(director->working_directory);
512 FDConnectTimeout = director->FDConnectTimeout;
513 SDConnectTimeout = director->SDConnectTimeout;
514 Dmsg0(10, "Director's configuration file reread.\n");
516 /* Now release saved resources, if no jobs using the resources */
518 free_saved_resources(table);
524 #if !defined(HAVE_WIN32)
525 sigprocmask(SIG_UNBLOCK, &set, NULL);
526 signal(SIGHUP, reload_config);
528 already_here = false;
532 * Make a quick check to see that we have all the
535 * **** FIXME **** this routine could be a lot more
536 * intelligent and comprehensive.
538 static bool check_resources()
545 job = (JOB *)GetNextRes(R_JOB, NULL);
546 director = (DIRRES *)GetNextRes(R_DIRECTOR, NULL);
548 Jmsg(NULL, M_FATAL, 0, _("No Director resource defined in %s\n"
549 "Without that I don't know who I am :-(\n"), configfile);
552 set_working_directory(director->working_directory);
553 if (!director->messages) { /* If message resource not specified */
554 director->messages = (MSGS *)GetNextRes(R_MSGS, NULL);
555 if (!director->messages) {
556 Jmsg(NULL, M_FATAL, 0, _("No Messages resource defined in %s\n"), configfile);
560 if (GetNextRes(R_DIRECTOR, (RES *)director) != NULL) {
561 Jmsg(NULL, M_FATAL, 0, _("Only one Director resource permitted in %s\n"),
565 /* tls_require implies tls_enable */
566 if (director->tls_require) {
568 director->tls_enable = true;
570 Jmsg(NULL, M_FATAL, 0, _("TLS required but not configured in Bacula.\n"));
575 if (!director->tls_certfile && director->tls_enable) {
576 Jmsg(NULL, M_FATAL, 0, _("\"TLS Certificate\" file not defined for Director \"%s\" in %s.\n"),
577 director->name(), configfile);
581 if (!director->tls_keyfile && director->tls_enable) {
582 Jmsg(NULL, M_FATAL, 0, _("\"TLS Key\" file not defined for Director \"%s\" in %s.\n"),
583 director->name(), configfile);
587 if ((!director->tls_ca_certfile && !director->tls_ca_certdir) && director->tls_enable && director->tls_verify_peer) {
588 Jmsg(NULL, M_FATAL, 0, _("Neither \"TLS CA Certificate\" or \"TLS CA"
589 " Certificate Dir\" are defined for Director \"%s\" in %s."
590 " At least one CA certificate store is required"
591 " when using \"TLS Verify Peer\".\n"),
592 director->name(), configfile);
596 /* If everything is well, attempt to initialize our per-resource TLS context */
597 if (OK && (director->tls_enable || director->tls_require)) {
598 /* Initialize TLS context:
599 * Args: CA certfile, CA certdir, Certfile, Keyfile,
600 * Keyfile PEM Callback, Keyfile CB Userdata, DHfile, Verify Peer */
601 director->tls_ctx = new_tls_context(director->tls_ca_certfile,
602 director->tls_ca_certdir, director->tls_certfile,
603 director->tls_keyfile, NULL, NULL, director->tls_dhfile,
604 director->tls_verify_peer);
606 if (!director->tls_ctx) {
607 Jmsg(NULL, M_FATAL, 0, _("Failed to initialize TLS context for Director \"%s\" in %s.\n"),
608 director->name(), configfile);
615 Jmsg(NULL, M_FATAL, 0, _("No Job records defined in %s\n"), configfile);
618 foreach_res(job, R_JOB) {
622 /* Handle Storage alists specifically */
623 JOB *jobdefs = job->jobdefs;
624 if (jobdefs->storage && !job->storage) {
626 job->storage = New(alist(10, not_owned_by_alist));
627 foreach_alist(st, jobdefs->storage) {
628 job->storage->append(st);
631 /* Handle RunScripts alists specifically */
632 if (jobdefs->RunScripts) {
635 if (!job->RunScripts) {
636 job->RunScripts = New(alist(10, not_owned_by_alist));
639 foreach_alist(rs, jobdefs->RunScripts) {
640 elt = copy_runscript(rs);
641 job->RunScripts->append(elt); /* we have to free it */
645 /* Transfer default items from JobDefs Resource */
646 for (i=0; job_items[i].name; i++) {
647 char **def_svalue, **svalue; /* string value */
648 int *def_ivalue, *ivalue; /* integer value */
649 bool *def_bvalue, *bvalue; /* bool value */
650 int64_t *def_lvalue, *lvalue; /* 64 bit values */
653 Dmsg4(1400, "Job \"%s\", field \"%s\" bit=%d def=%d\n",
654 job->name(), job_items[i].name,
655 bit_is_set(i, job->hdr.item_present),
656 bit_is_set(i, job->jobdefs->hdr.item_present));
658 if (!bit_is_set(i, job->hdr.item_present) &&
659 bit_is_set(i, job->jobdefs->hdr.item_present)) {
660 Dmsg2(400, "Job \"%s\", field \"%s\": getting default.\n",
661 job->name(), job_items[i].name);
662 offset = (char *)(job_items[i].value) - (char *)&res_all;
664 * Handle strings and directory strings
666 if (job_items[i].handler == store_str ||
667 job_items[i].handler == store_dir) {
668 def_svalue = (char **)((char *)(job->jobdefs) + offset);
669 Dmsg5(400, "Job \"%s\", field \"%s\" def_svalue=%s item %d offset=%u\n",
670 job->name(), job_items[i].name, *def_svalue, i, offset);
671 svalue = (char **)((char *)job + offset);
673 Pmsg1(000, _("Hey something is wrong. p=0x%lu\n"), *svalue);
675 *svalue = bstrdup(*def_svalue);
676 set_bit(i, job->hdr.item_present);
680 } else if (job_items[i].handler == store_res) {
681 def_svalue = (char **)((char *)(job->jobdefs) + offset);
682 Dmsg4(400, "Job \"%s\", field \"%s\" item %d offset=%u\n",
683 job->name(), job_items[i].name, i, offset);
684 svalue = (char **)((char *)job + offset);
686 Pmsg1(000, _("Hey something is wrong. p=0x%lu\n"), *svalue);
688 *svalue = *def_svalue;
689 set_bit(i, job->hdr.item_present);
691 * Handle alist resources
693 } else if (job_items[i].handler == store_alist_res) {
694 if (bit_is_set(i, job->jobdefs->hdr.item_present)) {
695 set_bit(i, job->hdr.item_present);
698 * Handle integer fields
699 * Note, our store_bit does not handle bitmaped fields
701 } else if (job_items[i].handler == store_bit ||
702 job_items[i].handler == store_pint ||
703 job_items[i].handler == store_jobtype ||
704 job_items[i].handler == store_level ||
705 job_items[i].handler == store_pint ||
706 job_items[i].handler == store_replace) {
707 def_ivalue = (int *)((char *)(job->jobdefs) + offset);
708 Dmsg5(400, "Job \"%s\", field \"%s\" def_ivalue=%d item %d offset=%u\n",
709 job->name(), job_items[i].name, *def_ivalue, i, offset);
710 ivalue = (int *)((char *)job + offset);
711 *ivalue = *def_ivalue;
712 set_bit(i, job->hdr.item_present);
714 * Handle 64 bit integer fields
716 } else if (job_items[i].handler == store_time ||
717 job_items[i].handler == store_size ||
718 job_items[i].handler == store_int64) {
719 def_lvalue = (int64_t *)((char *)(job->jobdefs) + offset);
720 Dmsg5(400, "Job \"%s\", field \"%s\" def_lvalue=%" lld " item %d offset=%u\n",
721 job->name(), job_items[i].name, *def_lvalue, i, offset);
722 lvalue = (int64_t *)((char *)job + offset);
723 *lvalue = *def_lvalue;
724 set_bit(i, job->hdr.item_present);
728 } else if (job_items[i].handler == store_bool) {
729 def_bvalue = (bool *)((char *)(job->jobdefs) + offset);
730 Dmsg5(400, "Job \"%s\", field \"%s\" def_bvalue=%d item %d offset=%u\n",
731 job->name(), job_items[i].name, *def_bvalue, i, offset);
732 bvalue = (bool *)((char *)job + offset);
733 *bvalue = *def_bvalue;
734 set_bit(i, job->hdr.item_present);
740 * Ensure that all required items are present
742 for (i=0; job_items[i].name; i++) {
743 if (job_items[i].flags & ITEM_REQUIRED) {
744 if (!bit_is_set(i, job->hdr.item_present)) {
745 Jmsg(NULL, M_ERROR_TERM, 0, _("\"%s\" directive in Job \"%s\" resource is required, but not found.\n"),
746 job_items[i].name, job->name());
750 /* If this triggers, take a look at lib/parse_conf.h */
751 if (i >= MAX_RES_ITEMS) {
752 Emsg0(M_ERROR_TERM, 0, _("Too many items in Job resource\n"));
755 if (!job->storage && !job->pool->storage) {
756 Jmsg(NULL, M_FATAL, 0, _("No storage specified in Job \"%s\" nor in Pool.\n"),
760 } /* End loop over Job res */
763 /* Loop over Consoles */
765 foreach_res(cons, R_CONSOLE) {
766 /* tls_require implies tls_enable */
767 if (cons->tls_require) {
769 cons->tls_enable = true;
771 Jmsg(NULL, M_FATAL, 0, _("TLS required but not configured in Bacula.\n"));
777 if (!cons->tls_certfile && cons->tls_enable) {
778 Jmsg(NULL, M_FATAL, 0, _("\"TLS Certificate\" file not defined for Console \"%s\" in %s.\n"),
779 cons->name(), configfile);
783 if (!cons->tls_keyfile && cons->tls_enable) {
784 Jmsg(NULL, M_FATAL, 0, _("\"TLS Key\" file not defined for Console \"%s\" in %s.\n"),
785 cons->name(), configfile);
789 if ((!cons->tls_ca_certfile && !cons->tls_ca_certdir) && cons->tls_enable && cons->tls_verify_peer) {
790 Jmsg(NULL, M_FATAL, 0, _("Neither \"TLS CA Certificate\" or \"TLS CA"
791 " Certificate Dir\" are defined for Console \"%s\" in %s."
792 " At least one CA certificate store is required"
793 " when using \"TLS Verify Peer\".\n"),
794 cons->name(), configfile);
797 /* If everything is well, attempt to initialize our per-resource TLS context */
798 if (OK && (cons->tls_enable || cons->tls_require)) {
799 /* Initialize TLS context:
800 * Args: CA certfile, CA certdir, Certfile, Keyfile,
801 * Keyfile PEM Callback, Keyfile CB Userdata, DHfile, Verify Peer */
802 cons->tls_ctx = new_tls_context(cons->tls_ca_certfile,
803 cons->tls_ca_certdir, cons->tls_certfile,
804 cons->tls_keyfile, NULL, NULL, cons->tls_dhfile, cons->tls_verify_peer);
806 if (!cons->tls_ctx) {
807 Jmsg(NULL, M_FATAL, 0, _("Failed to initialize TLS context for File daemon \"%s\" in %s.\n"),
808 cons->name(), configfile);
815 /* Loop over Clients */
817 foreach_res(client, R_CLIENT) {
818 /* tls_require implies tls_enable */
819 if (client->tls_require) {
821 client->tls_enable = true;
823 Jmsg(NULL, M_FATAL, 0, _("TLS required but not configured in Bacula.\n"));
829 if ((!client->tls_ca_certfile && !client->tls_ca_certdir) && client->tls_enable) {
830 Jmsg(NULL, M_FATAL, 0, _("Neither \"TLS CA Certificate\""
831 " or \"TLS CA Certificate Dir\" are defined for File daemon \"%s\" in %s.\n"),
832 client->name(), configfile);
836 /* If everything is well, attempt to initialize our per-resource TLS context */
837 if (OK && (client->tls_enable || client->tls_require)) {
838 /* Initialize TLS context:
839 * Args: CA certfile, CA certdir, Certfile, Keyfile,
840 * Keyfile PEM Callback, Keyfile CB Userdata, DHfile, Verify Peer */
841 client->tls_ctx = new_tls_context(client->tls_ca_certfile,
842 client->tls_ca_certdir, client->tls_certfile,
843 client->tls_keyfile, NULL, NULL, NULL,
846 if (!client->tls_ctx) {
847 Jmsg(NULL, M_FATAL, 0, _("Failed to initialize TLS context for File daemon \"%s\" in %s.\n"),
848 client->name(), configfile);
856 close_msg(NULL); /* close temp message handler */
857 init_msg(NULL, director->messages); /* open daemon message handler */
862 static bool check_catalog()
866 /* Loop over databases */
868 foreach_res(catalog, R_CATALOG) {
871 * Make sure we can open catalog, otherwise print a warning
872 * message because the server is probably not running.
874 db = db_init_database(NULL, catalog->db_name, catalog->db_user,
875 catalog->db_password, catalog->db_address,
876 catalog->db_port, catalog->db_socket,
877 catalog->mult_db_connections);
878 if (!db || !db_open_database(NULL, db)) {
879 Pmsg2(000, _("Could not open Catalog \"%s\", database \"%s\".\n"),
880 catalog->name(), catalog->db_name);
881 Jmsg(NULL, M_FATAL, 0, _("Could not open Catalog \"%s\", database \"%s\".\n"),
882 catalog->name(), catalog->db_name);
884 Jmsg(NULL, M_FATAL, 0, _("%s"), db_strerror(db));
885 Pmsg1(000, "%s", db_strerror(db));
886 db_close_database(NULL, db);
892 /* Loop over all pools, defining/updating them in each database */
894 foreach_res(pool, R_POOL) {
895 create_pool(NULL, db, pool, POOL_OP_UPDATE); /* update request */
898 /* Loop over all pools for updating RecyclePool */
899 foreach_res(pool, R_POOL) {
900 update_pool_recyclepool(NULL, db, pool);
904 foreach_res(store, R_STORAGE) {
907 if (store->media_type) {
908 bstrncpy(mr.MediaType, store->media_type, sizeof(mr.MediaType));
910 db_create_mediatype_record(NULL, db, &mr);
914 bstrncpy(sr.Name, store->name(), sizeof(sr.Name));
915 sr.AutoChanger = store->autochanger;
916 db_create_storage_record(NULL, db, &sr);
917 store->StorageId = sr.StorageId; /* set storage Id */
918 if (!sr.created) { /* if not created, update it */
919 db_update_storage_record(NULL, db, &sr);
922 /* tls_require implies tls_enable */
923 if (store->tls_require) {
925 store->tls_enable = true;
927 Jmsg(NULL, M_FATAL, 0, _("TLS required but not configured in Bacula.\n"));
932 if ((!store->tls_ca_certfile && !store->tls_ca_certdir) && store->tls_enable) {
933 Jmsg(NULL, M_FATAL, 0, _("Neither \"TLS CA Certificate\""
934 " or \"TLS CA Certificate Dir\" are defined for Storage \"%s\" in %s.\n"),
935 store->name(), configfile);
939 /* If everything is well, attempt to initialize our per-resource TLS context */
940 if (OK && (store->tls_enable || store->tls_require)) {
941 /* Initialize TLS context:
942 * Args: CA certfile, CA certdir, Certfile, Keyfile,
943 * Keyfile PEM Callback, Keyfile CB Userdata, DHfile, Verify Peer */
944 store->tls_ctx = new_tls_context(store->tls_ca_certfile,
945 store->tls_ca_certdir, store->tls_certfile,
946 store->tls_keyfile, NULL, NULL, NULL, true);
948 if (!store->tls_ctx) {
949 Jmsg(NULL, M_FATAL, 0, _("Failed to initialize TLS context for Storage \"%s\" in %s.\n"),
950 store->name(), configfile);
956 /* Loop over all counters, defining them in each database */
957 /* Set default value in all counters */
959 foreach_res(counter, R_COUNTER) {
960 /* Write to catalog? */
961 if (!counter->created && counter->Catalog == catalog) {
963 bstrncpy(cr.Counter, counter->name(), sizeof(cr.Counter));
964 cr.MinValue = counter->MinValue;
965 cr.MaxValue = counter->MaxValue;
966 cr.CurrentValue = counter->MinValue;
967 if (counter->WrapCounter) {
968 bstrncpy(cr.WrapCounter, counter->WrapCounter->name(), sizeof(cr.WrapCounter));
970 cr.WrapCounter[0] = 0; /* empty string */
972 if (db_create_counter_record(NULL, db, &cr)) {
973 counter->CurrentValue = cr.CurrentValue;
974 counter->created = true;
975 Dmsg2(100, "Create counter %s val=%d\n", counter->name(), counter->CurrentValue);
978 if (!counter->created) {
979 counter->CurrentValue = counter->MinValue; /* default value */
982 db_close_database(NULL, db);
984 /* Set type in global for debugging */
985 set_db_type(db_get_type());