X-Git-Url: http://git.tuebingen.mpg.de/?p=adu.git;a=blobdiff_plain;f=adu.c;h=7d8c9abd0191b6d4c84036bcc70e7e91d2cf03f3;hp=ed1b4fa32aee7dac5a7650f2074f8f37df2820d1;hb=a159b67466fcb6cc38b9daf855051ce807669bc5;hpb=e584cd6d5a3782ddeb6640f69534ab1664da2605 diff --git a/adu.c b/adu.c index ed1b4fa..7d8c9ab 100644 --- a/adu.c +++ b/adu.c @@ -1,4 +1,20 @@ -/** \file adu.c The main functions used by all modes of operation. */ +/* + * Copyright (C) 2008 Andre Noll + * + * Licensed under the GPL v2. For licencing details see COPYING. + */ + +/** \file adu.c \brief The main functions used by all modes of operation. */ + +/** + * \mainpage adu API reference + * + * - Modes of operation: \ref select.c, \ref create.c, \ref interactive.c + * - User handling: \ref user.c + * - Error handling: \ref error.h + * - Library-type functions: \ref fd.c, \ref format.c, \ref string.c, \ref portable_io.h, \ref bloom.c + */ + #include "adu.h" #include /* readdir() */ #include @@ -11,7 +27,14 @@ #include "string.h" #include "error.h" +/** Define the array of error descriptions. */ DEFINE_ERRLIST; + +/** + * The error code of the last called osl library function. + * + * \sa osl(). + */ int osl_errno; /** In case a signal is received, its number is stored here. */ @@ -23,6 +46,8 @@ struct gengetopt_args_info conf; /** Options passed to --select-options. */ struct select_args_info select_conf; +/** Computed database dir */ +char *database_dir; /** * The table containing the directory names and statistics. @@ -106,6 +131,7 @@ static void close_dir_table(void) if (!dir_table) return; + NOTICE_LOG("closing dir table\n"); ret = osl(osl_close_table(dir_table, OSL_MARK_CLEAN)); if (ret < 0) ERROR_LOG("failed to close dir table: %s\n", adu_strerror(-ret)); @@ -113,7 +139,7 @@ static void close_dir_table(void) dir_table = NULL; } -void close_all_tables(void) +static void close_all_tables(void) { close_dir_table(); close_user_tables(); @@ -124,6 +150,12 @@ static void signal_handler(int s) signum = s; } +/** + * Check whether to terminate adu. + * + * Check whether a signal was caught that should terminate the + * adu process. If yes, close all osl tables and exit gracefully. + */ void check_signals(void) { if (likely(!signum)) @@ -144,18 +176,36 @@ static int init_signals(void) return 1; } +/** + * Open the directory table. + * + * \param create If non-zero, create the table first. + * + * \return Standard. + */ int open_dir_table(int create) { - dir_table_desc.dir = adu_strdup(conf.database_dir_arg); + int ret; + if (dir_table) + return 1; + + dir_table_desc.dir = adu_strdup(database_dir); if (create) { - int ret = osl(osl_create_table(&dir_table_desc)); - if (ret < 0) { - free((char *)dir_table_desc.dir); - return ret; - } + INFO_LOG("creating database directory structure\n"); + ret = mkpath(dir_table_desc.dir, 0777); + if (ret < 0) + goto out; + NOTICE_LOG("creating dir table\n"); + ret = osl(osl_create_table(&dir_table_desc)); + if (ret < 0) + goto out; } + INFO_LOG("opening dir table\n"); return osl(osl_open_table(&dir_table_desc, &dir_table)); +out: + free((char *)dir_table_desc.dir); + return ret; } static int check_args(void) @@ -179,10 +229,9 @@ static int check_args(void) return 1; } -static int print_complete_help_and_die(void) +static void print_complete_help_and_die(void) { const char **line; - select_cmdline_parser_init(&select_conf); printf("%s-%s\n", CMDLINE_PARSER_PACKAGE, CMDLINE_PARSER_VERSION); printf("%s\n\n", gengetopt_args_info_purpose); @@ -205,23 +254,60 @@ static int print_complete_help_and_die(void) printf("Interactive commands:\n"); print_interactive_help(); + cmdline_parser_free(&conf); + select_cmdline_parser_free(&select_conf); exit(EXIT_FAILURE); } +static void get_database_dir_or_die(void) +{ + char *tmp; + + if (conf.database_dir_given) + tmp = adu_strdup(conf.database_dir_arg); + else + tmp = make_message("%s%s", + conf.database_root_arg, conf.base_dir_arg); + /* + * As we change the cwd during database creation, database_dir + * must be an absolute path. + */ + database_dir = absolute_path(tmp); + free(tmp); + if (database_dir) + return; + EMERG_LOG("failed to get absolute path of database dir\n"); + exit(EXIT_FAILURE); +} + +/** + * The main function of adu. + * + * \param argc Usual argument count. + * \param argv Usual argument vector. + * + * Check command line options, init the signal handlers and + * call the main function of the selected mode. + * + * \return \p EXIT_SUCCESS on success, \p EXIT_FAILURE otherwise. + */ int main(int argc, char **argv) { int ret; struct cmdline_parser_params params = { - .override = 0, + .override = 1, .initialize = 1, .check_required = 0, .check_ambiguity = 0, .print_errors = 0 }; + select_cmdline_parser_init(&select_conf); + cmdline_parser_init(&conf); /* ignore errors and print complete help if --help was given */ cmdline_parser_ext(argc, argv, &conf, ¶ms); if (conf.help_given || conf.detailed_help_given) print_complete_help_and_die(); + cmdline_parser_free(&conf); params.check_required = 1; params.check_ambiguity = 1; params.print_errors = 1; @@ -235,7 +321,7 @@ int main(int argc, char **argv) ret = init_signals(); if (ret < 0) goto out; - ret = -E_SYNTAX; + get_database_dir_or_die(); if (conf.select_given) ret = com_select(); else if (conf.create_given) @@ -245,9 +331,13 @@ int main(int argc, char **argv) if (ret < 0) goto out; out: + close_all_tables(); if (ret < 0) { ERROR_LOG("%s\n", adu_strerror(-ret)); return -EXIT_FAILURE; } + free(database_dir); + cmdline_parser_free(&conf); + select_cmdline_parser_free(&select_conf); return EXIT_SUCCESS; }