X-Git-Url: http://git.tuebingen.mpg.de/?p=paraslash.git;a=blobdiff_plain;f=afs.c;h=b6cce36f42e30cd5672d7e5cc9934cc2d659ca8f;hp=5623d7e995743dccbfa5ddfa782930d7b63c37cb;hb=7196e1a81b02d147dd43011a0762fd04397acdc6;hpb=177ea8ea46918a925c0d2d8a07e7fbe9f478a40c diff --git a/afs.c b/afs.c index 5623d7e9..b6cce36f 100644 --- a/afs.c +++ b/afs.c @@ -1,8 +1,4 @@ -/* - * Copyright (C) 2007 Andre Noll - * - * Licensed under the GPL v2. For licencing details see COPYING. - */ +/* Copyright (C) 2007 Andre Noll , see file COPYING. */ /** \file afs.c Paraslash's audio file selector. */ @@ -26,8 +22,8 @@ #include "string.h" #include "afh.h" #include "afs.h" -#include "server.h" #include "net.h" +#include "server.h" #include "ipc.h" #include "list.h" #include "sched.h" @@ -78,11 +74,6 @@ static struct afs_table afs_tables[NUM_AFS_TABLES] = { struct command_task { /** The file descriptor for the local socket. */ int fd; - /** - * Value sent by the command handlers to identify themselves as - * children of the running para_server. - */ - uint32_t cookie; /** The associated task structure. */ struct task *task; }; @@ -97,15 +88,6 @@ static struct signal_task *signal_task; static enum play_mode current_play_mode; static char *current_mop; /* mode or playlist specifier. NULL means dummy mood */ -/** - * A random number used to "authenticate" the connection. - * - * para_server picks this number by random before it forks the afs process. The - * command handlers know this number as well and write it to the afs socket, - * together with the id of the shared memory area which contains the payload of - * the afs command. A local process has to know this number to abuse the afs - * service provided by the local socket. - */ extern uint32_t afs_socket_cookie; /** @@ -384,8 +366,8 @@ int for_each_matching_row(struct pattern_match_data *pmd) */ int string_compare(const struct osl_object *obj1, const struct osl_object *obj2) { - const char *str1 = (const char *)obj1->data; - const char *str2 = (const char *)obj2->data; + const char *str1 = obj1->data; + const char *str2 = obj2->data; return strncmp(str1, str2, PARA_MIN(obj1->size, obj2->size)); } @@ -436,13 +418,13 @@ static int pass_afd(int fd, char *buf, size_t size) */ static int open_next_audio_file(void) { - struct audio_file_data afd; - int ret, shmid; + int ret, shmid, fd; char buf[8]; - ret = open_and_update_audio_file(&afd); + ret = open_and_update_audio_file(&fd); if (ret < 0) { - PARA_ERROR_LOG("%s\n", para_strerror(-ret)); + if (ret != -OSL_ERRNO_TO_PARA_ERROR(E_OSL_RB_KEY_NOT_FOUND)) + PARA_ERROR_LOG("%s\n", para_strerror(-ret)); goto no_admissible_files; } shmid = ret; @@ -452,8 +434,8 @@ static int open_next_audio_file(void) } *(uint32_t *)buf = NEXT_AUDIO_FILE; *(uint32_t *)(buf + 4) = (uint32_t)shmid; - ret = pass_afd(afd.fd, buf, 8); - close(afd.fd); + ret = pass_afd(fd, buf, 8); + close(fd); if (ret >= 0) return ret; destroy: @@ -607,8 +589,9 @@ static int com_select_callback(struct afs_callback_arg *aca) para_printf(&aca->pbout, "activating dummy mood\n"); activate_mood_or_playlist(NULL, &num_admissible, NULL); out: - para_printf(&aca->pbout, "activated %s (%d admissible files)\n", - current_mop? current_mop : "dummy mood", num_admissible); + para_printf(&aca->pbout, "activated %s (%d admissible file%s)\n", + current_mop? current_mop : "dummy mood", num_admissible, + num_admissible == 1? "" : "s"); free_lpr: lls_free_parse_result(aca->lpr, cmd); return ret; @@ -656,16 +639,18 @@ static int setup_command_socket_or_die(void) return socket_fd; } +static char *database_dir; + static void close_afs_tables(void) { int i; PARA_NOTICE_LOG("closing afs_tables\n"); for (i = 0; i < NUM_AFS_TABLES; i++) afs_tables[i].close(); + free(database_dir); + database_dir = NULL; } -static char *database_dir; - static void get_database_dir(void) { if (!database_dir) { @@ -703,8 +688,7 @@ static int open_afs_tables(void) ret = afs_tables[i].open(database_dir); if (ret >= 0) continue; - PARA_ERROR_LOG("%s init: %s\n", afs_tables[i].name, - para_strerror(-ret)); + PARA_ERROR_LOG("could not open %s\n", afs_tables[i].name); break; } if (ret >= 0) @@ -884,7 +868,7 @@ static int execute_server_command(fd_set *rfds) } /* returns 0 if no data available, 1 else */ -static int execute_afs_command(int fd, fd_set *rfds, uint32_t expected_cookie) +static int execute_afs_command(int fd, fd_set *rfds) { uint32_t cookie; int query_shmid; @@ -902,9 +886,9 @@ static int execute_afs_command(int fd, fd_set *rfds, uint32_t expected_cookie) return 1; } cookie = *(uint32_t *)buf; - if (cookie != expected_cookie) { + if (cookie != afs_socket_cookie) { PARA_NOTICE_LOG("received invalid cookie (got %u, expected %u)\n", - (unsigned)cookie, (unsigned)expected_cookie); + (unsigned)cookie, (unsigned)afs_socket_cookie); return 1; } query_shmid = *(int *)(buf + sizeof(cookie)); @@ -942,7 +926,7 @@ static int command_post_select(struct sched *s, void *context) } /* Check the list of connected clients. */ list_for_each_entry_safe(client, tmp, &afs_client_list, node) { - ret = execute_afs_command(client->fd, &s->rfds, ct->cookie); + ret = execute_afs_command(client->fd, &s->rfds); if (ret == 0) { /* prevent bogus connection flooding */ struct timeval diff; tv_diff(now, &client->connect_time, &diff); @@ -973,11 +957,10 @@ static int command_post_select(struct sched *s, void *context) return 0; } -static void register_command_task(uint32_t cookie, struct sched *s) +static void register_command_task(struct sched *s) { struct command_task *ct = &command_task_struct; ct->fd = setup_command_socket_or_die(); - ct->cookie = cookie; ct->task = task_register(&(struct task_info) { .name = "afs command", @@ -990,10 +973,9 @@ static void register_command_task(uint32_t cookie, struct sched *s) /** * Initialize the audio file selector process. * - * \param cookie The value used for "authentication". * \param socket_fd File descriptor used for communication with the server. */ -__noreturn void afs_init(uint32_t cookie, int socket_fd) +__noreturn void afs_init(int socket_fd) { static struct sched s; int i, ret; @@ -1009,10 +991,9 @@ __noreturn void afs_init(uint32_t cookie, int socket_fd) ret = mark_fd_nonblocking(server_socket); if (ret < 0) goto out_close; - PARA_INFO_LOG("server_socket: %d, afs_socket_cookie: %u\n", - server_socket, (unsigned) cookie); + PARA_INFO_LOG("server_socket: %d\n", server_socket); init_admissible_files(OPT_STRING_VAL(AFS_INITIAL_MODE)); - register_command_task(cookie, &s); + register_command_task(&s); s.default_timeout.tv_sec = 0; s.default_timeout.tv_usec = 999 * 1000; ret = write(socket_fd, "\0", 1); @@ -1024,9 +1005,14 @@ __noreturn void afs_init(uint32_t cookie, int socket_fd) } ret = schedule(&s); sched_shutdown(&s); + close_current_mood(); out_close: close_afs_tables(); out: + signal_shutdown(signal_task); + free_status_items(); + free(current_mop); + free_lpr(); if (ret < 0) PARA_EMERG_LOG("%s\n", para_strerror(-ret)); exit(EXIT_FAILURE); @@ -1038,6 +1024,7 @@ static int com_init_callback(struct afs_callback_arg *aca) int i, ret; close_afs_tables(); + get_database_dir(); for (i = 0; i < NUM_AFS_TABLES; i++) { struct afs_table *t = &afs_tables[i]; @@ -1056,7 +1043,8 @@ static int com_init_callback(struct afs_callback_arg *aca) } ret = open_afs_tables(); if (ret < 0) - para_printf(&aca->pbout, "cannot open afs tables\n"); + para_printf(&aca->pbout, "cannot open afs tables: %s\n", + para_strerror(-ret)); out: return ret; }