From: Andre Noll Date: Sat, 23 Mar 2019 16:42:12 +0000 (+0100) Subject: Merge branch 'refs/heads/t/mixer-fix' X-Git-Tag: v0.6.3~46 X-Git-Url: http://git.tuebingen.mpg.de/?p=paraslash.git;a=commitdiff_plain;h=6bded356ec89b1344049ff702e6c6babaeccd439;hp=176d4e57f7381f6215f2baf3b07f859bb4c72e76 Merge branch 'refs/heads/t/mixer-fix' Two bug fixes for the sleep mode of para_mixer. Started on 2018-07-07, cooking since 2018-08-19. * refs/heads/t/mixer-fix: mixer: sleep: Change to next file at fade-in time. mixer: sleep: Change to fade-in mood later. --- diff --git a/Makefile.real b/Makefile.real index dae48f0e..5df27bad 100644 --- a/Makefile.real +++ b/Makefile.real @@ -18,7 +18,7 @@ uname_s := $(shell uname -s 2>/dev/null || echo "UNKNOWN_OS") uname_rs := $(shell uname -rs) cc_version := $(shell $(CC) --version | head -n 1) GIT_VERSION := $(shell ./GIT-VERSION-GEN git-version.h) -COPYRIGHT_YEAR := 2018 +COPYRIGHT_YEAR := 2019 ifeq ("$(origin O)", "command line") build_dir := $(O) @@ -110,7 +110,6 @@ CPPFLAGS += -DBUILD_DATE='"$(build_date)"' CPPFLAGS += -DLOGLEVELS='$(LOGLEVELS)' CPPFLAGS += -DUNAME_RS='"$(uname_rs)"' CPPFLAGS += -DCC_VERSION='"$(cc_version)"' -CPPFLAGS += -I/usr/local/include CPPFLAGS += -I$(lls_suite_dir) CPPFLAGS += -I$(yy_build_dir) CPPFLAGS += $(lopsub_cppflags) @@ -191,7 +190,7 @@ $(object_dir)/spx%.o: CPPFLAGS += $(speex_cppflags) $(object_dir)/flac%.o: CPPFLAGS += $(flac_cppflags) $(object_dir)/mp3_afh.o: CPPFLAGS += $(id3tag_cppflags) -$(object_dir)/crypt.o: CPPFLAGS += $(openssl_cppflags) +$(object_dir)/openssl.o: CPPFLAGS += $(openssl_cppflags) $(object_dir)/gcrypt.o: CPPFLAGS += $(gcrypt_cppflags) $(object_dir)/ao_write.o: CPPFLAGS += $(ao_cppflags) $(object_dir)/alsa%.o: CPPFLAGS += $(alsa_cppflags) diff --git a/afs.c b/afs.c index 4fe2140b..d9cddeb8 100644 --- a/afs.c +++ b/afs.c @@ -589,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; diff --git a/afs.h b/afs.h index b0d283f6..cfa9cc6d 100644 --- a/afs.h +++ b/afs.h @@ -285,10 +285,12 @@ int playlist_check_callback(struct afs_callback_arg *aca); struct para_buffer *pb, void *data); \ extern struct osl_table *table_name ## _table; +/** \cond blob_symbols */ DECLARE_BLOB_SYMBOLS(lyrics, lyr); DECLARE_BLOB_SYMBOLS(images, img); DECLARE_BLOB_SYMBOLS(moods, mood); DECLARE_BLOB_SYMBOLS(playlists, pl); +/** \endcond blob_symbols */ /** The columns of an abstract blob table. */ enum blob_table_columns { diff --git a/aft.c b/aft.c index 5d4e6477..0db2c580 100644 --- a/aft.c +++ b/aft.c @@ -50,46 +50,28 @@ static struct ls_data status_item_ls_data; /** The different sorting methods of the ls command. */ enum ls_sorting_method { - /** -sp (default) */ - LS_SORT_BY_PATH, - /** -ss */ - LS_SORT_BY_SCORE, - /** -sl */ - LS_SORT_BY_LAST_PLAYED, - /** -sn */ - LS_SORT_BY_NUM_PLAYED, - /** -sf */ - LS_SORT_BY_FREQUENCY, - /** -sc */ - LS_SORT_BY_CHANNELS, - /** -si */ - LS_SORT_BY_IMAGE_ID, - /** -sy */ - LS_SORT_BY_LYRICS_ID, - /** -sb */ - LS_SORT_BY_BITRATE, - /** -sd */ - LS_SORT_BY_DURATION, - /** -sa */ - LS_SORT_BY_AUDIO_FORMAT, - /** -sh */ - LS_SORT_BY_HASH, + LS_SORT_BY_PATH, /**< -s=p (default) */ + LS_SORT_BY_SCORE, /**< -s=s */ + LS_SORT_BY_LAST_PLAYED, /**< -s=l */ + LS_SORT_BY_NUM_PLAYED, /**< -s=n */ + LS_SORT_BY_FREQUENCY, /**< -s=f */ + LS_SORT_BY_CHANNELS, /**< -s=c */ + LS_SORT_BY_IMAGE_ID, /**< -s=i */ + LS_SORT_BY_LYRICS_ID, /**< -s=y */ + LS_SORT_BY_BITRATE, /**< -s=b */ + LS_SORT_BY_DURATION, /**< -s=d */ + LS_SORT_BY_AUDIO_FORMAT, /**< -s=a */ + LS_SORT_BY_HASH, /**< -s=h */ }; /** The different listing modes of the ls command. */ enum ls_listing_mode { - /** Default listing mode. */ - LS_MODE_SHORT, - /** -l or -ll */ - LS_MODE_LONG, - /** -lv */ - LS_MODE_VERBOSE, - /** -lm */ - LS_MODE_MBOX, - /** -lc */ - LS_MODE_CHUNKS, - /** -lp */ - LS_MODE_PARSER, + LS_MODE_SHORT, /**< Default listing mode. */ + LS_MODE_LONG, /**< -l or -l=l */ + LS_MODE_VERBOSE, /** -l=v */ + LS_MODE_MBOX, /** -l=m */ + LS_MODE_CHUNKS, /** -l=c */ + LS_MODE_PARSER, /** -l=p */ }; /** @@ -983,13 +965,18 @@ out: WRITE_STATUS_ITEM(pb, SI_file_size, "%ld\n", statbuf.st_size / 1024); } +/** + * Deallocate and invalidate the status item strings. + * + * This needs to be a public function so that afs.c can call it on shutdown. + */ void free_status_items(void) { freep(&status_items); freep(&parser_friendly_status_items); } -static int make_status_items(void) +static void make_status_items(void) { const struct lls_command *cmd = SERVER_CMD_CMD_PTR(LS); char *argv[] = {"ls", "--admissible", "--listing-mode=verbose"}; @@ -1000,7 +987,7 @@ static int make_status_items(void) free_status_items(); if (!status_item_ls_data.path) /* no audio file open */ - return 0; + return; ret = lls_parse(ARRAY_SIZE(argv), argv, cmd, &opts.lpr, NULL); assert(ret >= 0); time(¤t_time); @@ -1020,10 +1007,12 @@ static int make_status_items(void) parser_friendly_status_items = pb.buf; ret = 1; out: - if (ret < 0) + if (ret < 0) { + PARA_WARNING_LOG("could not create status items: %s\n", + para_strerror(-ret)); free_status_items(); + } lls_free_parse_result(opts.lpr, cmd); - return ret; } /** diff --git a/ao_write.c b/ao_write.c index 4258803f..447dea84 100644 --- a/ao_write.c +++ b/ao_write.c @@ -87,7 +87,7 @@ static int aow_set_sample_format(unsigned sample_rate, unsigned channels, case SF_U8: case SF_U16_LE: case SF_U16_BE: - return -E_AO_BAD_SAMPLE_FORMAT; + return -E_BAD_SAMPLE_FORMAT; case SF_S8: /* no need to set byte_format */ result->bits = 8; @@ -159,8 +159,8 @@ static void aow_show_drivers(void) if (info->type == AO_TYPE_FILE) continue; - PARA_DEBUG_LOG("%s: %s", info->short_name, info->name); - PARA_DEBUG_LOG("priority: %d", info->priority); + PARA_DEBUG_LOG("name: %s: %s\n", info->short_name, info->name); + PARA_DEBUG_LOG("priority: %d\n", info->priority); for (j = 0; j < info->option_count; j++) { tmp = make_message("%s%s%s", keys? keys : "", keys? ", " : "", @@ -168,9 +168,9 @@ static void aow_show_drivers(void) free(keys); keys = tmp; } - PARA_DEBUG_LOG("keys: %s", keys? keys : "[none]"); + PARA_DEBUG_LOG("keys: %s\n", keys? keys : "[none]"); free(keys); - PARA_DEBUG_LOG("comment: %s", info->comment? + PARA_DEBUG_LOG("comment: %s\n", info->comment? info->comment : "[none]"); } } @@ -244,7 +244,7 @@ fail: return ret; } -__noreturn static void *aow_play(void *priv) +static void *aow_play(void *priv) { struct writer_node *wn = priv; struct private_aow_data *pawd = wn->private_data; diff --git a/blob.c b/blob.c index 890b9226..4ecbc45b 100644 --- a/blob.c +++ b/blob.c @@ -72,7 +72,6 @@ static struct osl_column_description blob_cols[] = { /** Define a pointer to an osl blob table with a canonical name. */ #define DEFINE_BLOB_TABLE_PTR(table_name) struct osl_table *table_name ## _table; - /** Define a blob table. */ #define INIT_BLOB_TABLE(table_name) \ DEFINE_BLOB_TABLE_DESC(table_name); \ @@ -104,7 +103,7 @@ static int print_blob(struct osl_table *table, struct osl_row *row, para_printf(&aca->pbout, "cannot list %s\n", name); return ret; } - id = *(uint32_t *)obj.data; + id = read_u32(obj.data); para_printf(&aca->pbout, "%u\t%s\n", id, name); return 1; } @@ -121,6 +120,7 @@ static int com_lsblob_callback(const struct lls_command * const cmd, .action = print_blob, }; int ret; + ret = lls_deserialize_parse_result(aca->query.data, cmd, &aca->lpr); pmd.lpr = aca->lpr; assert(ret >= 0); @@ -176,6 +176,7 @@ static int com_catblob_callback(const struct lls_command * const cmd, .data = &aca->fd, .action = cat_blob }; + ret = lls_deserialize_parse_result(aca->query.data, cmd, &aca->lpr); assert(ret >= 0); pmd.lpr = aca->lpr; @@ -207,6 +208,7 @@ static int remove_blob(struct osl_table *table, struct osl_row *row, { struct afs_callback_arg *aca = data; int ret = osl(osl_del_row(table, row)); + if (ret < 0) { para_printf(&aca->pbout, "cannot remove %s\n", name); return ret; @@ -226,6 +228,7 @@ static int com_rmblob_callback(const struct lls_command * const cmd, .data = aca, .action = remove_blob }; + ret = lls_deserialize_parse_result(aca->query.data, cmd, &aca->lpr); assert(ret >= 0); pmd.lpr = aca->lpr; @@ -263,7 +266,8 @@ static int com_addblob_callback(__a_unused const struct lls_command * const cmd, struct osl_object objs[NUM_BLOB_COLUMNS]; char *name = aca->query.data; size_t name_len = strlen(name) + 1; - uint32_t id; + uint32_t id = (uint32_t)-1; /* STFU, gcc */ + char id_buf[sizeof(id)]; unsigned num_rows; int ret; @@ -271,10 +275,15 @@ static int com_addblob_callback(__a_unused const struct lls_command * const cmd, if (ret < 0) goto out; if (!num_rows) { /* this is the first entry ever added */ - /* insert dummy row containing the id */ - id = 2; /* this entry will be entry #1, so 2 is the next */ - objs[BLOBCOL_ID].data = &id; - objs[BLOBCOL_ID].size = sizeof(id); + /* + * Insert dummy row containing the next free ID. Since we are + * about to insert the first blob with ID 1, the next free ID + * will be 2. + */ + id = 2U; + write_u32(id_buf, id); + objs[BLOBCOL_ID].data = id_buf; + objs[BLOBCOL_ID].size = sizeof(id_buf); objs[BLOBCOL_NAME].data = ""; objs[BLOBCOL_NAME].size = 1; objs[BLOBCOL_DEF].data = ""; @@ -293,7 +302,7 @@ static int com_addblob_callback(__a_unused const struct lls_command * const cmd, ret = osl(osl_get_object(table, row, BLOBCOL_ID, &obj)); if (ret < 0) goto out; - id = *(uint32_t *)obj.data; + id = read_u32(obj.data); obj.data = name + name_len; obj.size = aca->query.size - name_len; ret = osl(osl_update_object(table, row, BLOBCOL_DEF, &obj)); @@ -308,15 +317,17 @@ static int com_addblob_callback(__a_unused const struct lls_command * const cmd, ret = osl(osl_get_object(table, row, BLOBCOL_ID, &obj)); if (ret < 0) goto out; - id = *(uint32_t *)obj.data + 1; - obj.data = &id; + id = read_u32(obj.data) + 1; + write_u32(id_buf, id); + obj.data = &id_buf; ret = osl(osl_update_object(table, row, BLOBCOL_ID, &obj)); if (ret < 0) goto out; } id--; - objs[BLOBCOL_ID].data = &id; - objs[BLOBCOL_ID].size = sizeof(id); + write_u32(id_buf, id); + objs[BLOBCOL_ID].data = &id_buf; + objs[BLOBCOL_ID].size = sizeof(id_buf); objs[BLOBCOL_NAME].data = name; objs[BLOBCOL_NAME].size = name_len; objs[BLOBCOL_DEF].data = name + name_len; @@ -374,7 +385,7 @@ again: * * This function is called from the addblob command handlers to instruct the * afs process to store the input in a blob table. Input is read and decrypted - * from the file descriptor given by cc and appended to arg_obj, which contains + * from the file descriptor given by cc and appended to a buffer which also contains * the name of the blob to create. The combined buffer is made available to the * afs process via the callback method. */ @@ -509,7 +520,6 @@ static int blob_get_name_by_id(struct osl_table *table, uint32_t id, return blob_get_name_by_id(table_name ## _table, id, name); \ } - static int blob_get_def_by_name(struct osl_table *table, char *name, struct osl_object *def) { @@ -561,6 +571,7 @@ static int blob_get_name_and_def_by_row(struct osl_table *table, { struct osl_object obj; int ret = osl(osl_get_object(table, row, BLOBCOL_NAME, &obj)); + if (ret < 0) return ret; *name = obj.data; @@ -596,6 +607,7 @@ static int blob_open(struct osl_table **table, const char *dir) { int ret; + desc->dir = dir; ret = osl(osl_open_table(desc, table)); if (ret >= 0) diff --git a/check_wav.c b/check_wav.c index f0990bf8..89ebdacc 100644 --- a/check_wav.c +++ b/check_wav.c @@ -11,6 +11,7 @@ #include "buffer_tree.h" #include "error.h" #include "check_wav.h" +#include "portable_io.h" /** Length of a standard wav header. */ #define WAV_HEADER_LEN 44 @@ -155,9 +156,9 @@ int check_wav_post_select(struct check_wav_context *cwc) PARA_INFO_LOG("found wav header\n"); cwc->state = CWS_HAVE_HEADER; /* Only set those values which have not already been set. */ - cwc->channels = (unsigned)a[22]; - cwc->sample_rate = a[24] + (a[25] << 8) + (a[26] << 16) + (a[27] << 24); - bps = a[34] + ((unsigned)a[35] << 8); + cwc->channels = a[22]; + cwc->sample_rate = read_u32(a + 24); + bps = read_u16(a + 34); if (bps != 8 && bps != 16) { PARA_WARNING_LOG("%u bps not supported, assuming 16\n", bps); diff --git a/command.c b/command.c index 6adb9455..67f6bf3c 100644 --- a/command.c +++ b/command.c @@ -279,7 +279,7 @@ static int check_sender_args(struct command_context *cc, } /** - * Send a sideband packet through a blocking file descriptor. + * Receive a sideband packet from a blocking file descriptor. * * \param scc fd and crypto keys. * \param expected_band The expected band designator. diff --git a/daemon.c b/daemon.c index bfa81487..a4e2f319 100644 --- a/daemon.c +++ b/daemon.c @@ -146,6 +146,22 @@ void daemon_set_loglevel(const char *loglevel) me->loglevel = ret; } +/** + * Register functions to be called before and after a message is logged. + * + * \param pre_log_hook Called before the message is logged. + * \param post_log_hook Called after the message is logged. + * + * The purpose of this function is to provide a primitive for multi-threaded + * applications to serialize the access to the log facility, preventing + * interleaving log messages. This can be achieved by having the pre-log hook + * acquire a lock which blocks the other threads on the attempt to log a + * message at the same time. The post-log hook is responsible for releasing + * the lock. + * + * If these hooks are unnecessary, for example because the application is + * single-threaded, this function does not need to be called. + */ void daemon_set_hooks(void (*pre_log_hook)(void), void (*post_log_hook)(void)) { me->pre_log_hook = pre_log_hook; diff --git a/error.h b/error.h index 02f42246..8f4f9bb1 100644 --- a/error.h +++ b/error.h @@ -24,7 +24,6 @@ PARA_ERROR(AO_APPEND_OPTION, "ao append option: memory allocation failure"), \ PARA_ERROR(AO_BAD_DRIVER, "ao: invalid driver"), \ PARA_ERROR(AO_BAD_OPTION, "ao option is not of type key:value"), \ - PARA_ERROR(AO_BAD_SAMPLE_FORMAT, "ao: unsigned sample formats not supported"), \ PARA_ERROR(AO_DEFAULT_DRIVER, "ao: no usable output device"), \ PARA_ERROR(AO_EOF, "ao: end of file"), \ PARA_ERROR(AO_FILE_NOT_SUPP, "ao: file io drivers not supported"), \ @@ -255,8 +254,9 @@ enum para_error_codes {PARA_ERRORS}; #undef PARA_ERROR #define PARA_ERROR(err, msg) msg -/** Array of error strings. */ +/** All .c files need the declararation of the array of error strings. */ extern const char * const para_errlist[]; +/** Exactly one .c file per executable must define the array. */ #define DEFINE_PARA_ERRLIST const char * const para_errlist[] = {PARA_ERRORS} /** diff --git a/gcrypt.c b/gcrypt.c index ff4dab37..694c0adb 100644 --- a/gcrypt.c +++ b/gcrypt.c @@ -237,7 +237,7 @@ static int read_bignum(unsigned char *start, unsigned char *end, gcry_mpi_t *bn, PARA_DEBUG_LOG("bn_size %d (0x%x)\n", bn_size, (unsigned)bn_size); gret = gcry_mpi_scan(bn, GCRYMPI_FMT_STD, cp, bn_size, NULL); if (gret) { - PARA_ERROR_LOG("%s while scanning n\n", + PARA_ERROR_LOG("gcry_mpi_scan: %s\n", gcry_strerror(gcry_err_code(gret))); return-E_MPI_SCAN; } diff --git a/interactive.c b/interactive.c index 190cdf29..a8197308 100644 --- a/interactive.c +++ b/interactive.c @@ -762,17 +762,25 @@ int i9e_print_completions(struct i9e_completer *completers) ci.argc = create_argv(ci.buffer, " ", &ci.argv); ci.word_num = compute_word_num(ci.buffer, " ", ci.point); + /* determine the current word to complete */ end = ci.buffer + ci.point; + + if (*end == ' ') { + if (ci.point == 0 || ci.buffer[ci.point - 1] == ' ') { + ci.word = para_strdup(NULL); + goto create_matches; + } else /* The cursor is positioned right after a word */ + end--; + } for (p = end; p > ci.buffer && *p != ' '; p--) ; /* nothing */ if (*p == ' ') p++; - n = end - p + 1; ci.word = para_malloc(n + 1); strncpy(ci.word, p, n); ci.word[n] = '\0'; - +create_matches: PARA_DEBUG_LOG("line: %s, point: %d (%c), wordnum: %d, word: %s\n", ci.buffer, ci.point, ci.buffer[ci.point], ci.word_num, ci.word); if (ci.word_num == 0) diff --git a/m4/lls/play.suite.m4 b/m4/lls/play.suite.m4 index 4af2a05a..57a9377e 100644 --- a/m4/lls/play.suite.m4 +++ b/m4/lls/play.suite.m4 @@ -9,10 +9,11 @@ version-string = GIT_VERSION() [description] para_play operates either in command mode or in insert mode. In insert mode it presents a prompt and allows the user to enter commands like - stop, play, pause etc. In command mode the current audio file and the - playback position are shown and the program reads single key strokes - from stdin. Keys may be mapped to commands so that the configured - command is executed when a mapped key is pressed. + play, pause, quit, etc. In command mode the current audio file and the + playback position are shown instead of the prompt/command line, and + the program reads single key strokes from stdin. Keys may be mapped + to commands so that the configured command is executed whenever a + mapped key is pressed. [/description] m4_include(common-option-section.m4) m4_include(help.m4) diff --git a/m4/lls/write_cmd.suite.m4 b/m4/lls/write_cmd.suite.m4 index 9d8ee75a..102afed1 100644 --- a/m4/lls/write_cmd.suite.m4 +++ b/m4/lls/write_cmd.suite.m4 @@ -38,8 +38,9 @@ caption = writers arg_info = required_arg arg_type = string [help] - If this is not given, the driver with the highest priority (see below) - will be used. + If this is not given, the driver with the highest priority will be + used. The list of available drivers and their priorities is shown in + debug mode. [/help] [option ao-option] short_opt = o @@ -51,7 +52,7 @@ caption = writers [help] For each time this option is given, the supplied key-value pair is appended to the list of options for the driver. Invalid keys are - silently ignored. + silently ignored. The list of available keys is shown in debug mode. [/help] [subcommand oss] purpose = output plugin for the Open Sound System @@ -62,18 +63,6 @@ caption = writers arg_info = required_arg arg_type = string default_val = /dev/dsp -[subcommand osx] - purpose = output plugin for Mac OS coreaudio - [option numbuffers] - short_opt = n - summary = number of audio buffers to allocate - typestr = num - arg_info = required_arg - arg_type = uint32 - default_val = 20 - [help] - Increase if you get buffer underruns. - [/help] [subcommand file] purpose = output plugin that writes to a local file [option filename] diff --git a/mixer.c b/mixer.c index 4ceaba9c..efa42b93 100644 --- a/mixer.c +++ b/mixer.c @@ -1,6 +1,6 @@ /* Copyright (C) 1998 Andre Noll , see file COPYING. */ -/** \file mixer.c A volume fader and alarm clock for OSS. */ +/** \file mixer.c A volume fader and alarm clock. */ #include #include @@ -529,7 +529,7 @@ int main(int argc, char *argv[]) } if (ret < 0) goto close_mixer; - ret = (*(mixer_subcommand_handler_t *)(lls_user_data(cmd)))(m ,h); + ret = (*(mixer_subcommand_handler_t *)(lls_user_data(cmd)))(m, h); close_mixer: m->close(&h); free_sub_lpr: diff --git a/mp3_afh.c b/mp3_afh.c index 42dd7539..471efd99 100644 --- a/mp3_afh.c +++ b/mp3_afh.c @@ -63,8 +63,6 @@ static const int mp3info_bitrate[2][3][14] = { }; static const int frame_size_index[] = {24000, 72000, 72000}; -static const char *mode_text[] = {"stereo", "joint stereo", "dual channel", "mono", "invalid"}; - #ifdef HAVE_ID3TAG #include @@ -433,10 +431,13 @@ static int header_frequency(struct mp3header *h) return frequencies[h->version][h->freq]; } -static const char *header_mode(struct mp3header *h) +static const char *header_mode(const struct mp3header *h) { - if (h->mode > 4) - h->mode = 4; /* invalid */ + const char * const mode_text[] = {"stereo", "joint stereo", + "dual channel", "mono"}; + + if (h->mode >= ARRAY_SIZE(mode_text)) + return "invalid"; return mode_text[h->mode]; } diff --git a/net.c b/net.c index ba19408e..91200fc0 100644 --- a/net.c +++ b/net.c @@ -10,18 +10,6 @@ #include #include #include - -/* At least NetBSD needs these. */ -#ifndef AI_V4MAPPED -#define AI_V4MAPPED 0 -#endif -#ifndef AI_ALL -#define AI_ALL 0 -#endif -#ifndef AI_ADDRCONFIG -#define AI_ADDRCONFIG 0 -#endif - #include #include "error.h" @@ -886,14 +874,13 @@ int dccp_available_ccids(uint8_t **ccid_array) * The first call to this function tries to bind a socket to the abstract name * space. The result of this test is stored in a static variable. Subsequent * calls read this variable and create abstract sockets on systems that support - * them. + * them. If a NULL pointer is passed as the name, the function only + * initializes the static variable. */ static int init_unix_addr(struct sockaddr_un *u, const char *name) { static int use_abstract; - if (strlen(name) + 1 >= UNIX_PATH_MAX) - return -E_NAME_TOO_LONG; memset(u->sun_path, 0, UNIX_PATH_MAX); u->sun_family = PF_UNIX; if (use_abstract == 0) { /* executed only once */ @@ -907,6 +894,10 @@ static int init_unix_addr(struct sockaddr_un *u, const char *name) PARA_NOTICE_LOG("%susing abstract socket namespace\n", use_abstract == 1? "" : "not "); } + if (!name) + return 0; + if (strlen(name) + 1 >= UNIX_PATH_MAX) + return -E_NAME_TOO_LONG; strcpy(u->sun_path + (use_abstract == 1? 1 : 0), name); return 1; } @@ -931,7 +922,7 @@ int create_local_socket(const char *name) int fd, ret; ret = init_unix_addr(&unix_addr, name); - if (ret < 0) + if (ret <= 0) /* error, or name was NULL */ return ret; ret = socket(PF_UNIX, SOCK_STREAM, 0); if (ret < 0) diff --git a/openssl.c b/openssl.c index 7d5bb25d..4895e176 100644 --- a/openssl.c +++ b/openssl.c @@ -124,11 +124,11 @@ static int read_rsa_bignums(const unsigned char *blob, int blen, RSA **result) return -E_BIGNUM; ret = read_bignum(p, end - p, &e); if (ret < 0) - goto fail; + goto free_rsa; p += ret; ret = read_bignum(p, end - p, &n); if (ret < 0) - goto fail; + goto free_e; #ifdef HAVE_RSA_SET0_KEY RSA_set0_key(rsa, n, e, NULL); #else @@ -137,7 +137,9 @@ static int read_rsa_bignums(const unsigned char *blob, int blen, RSA **result) #endif *result = rsa; return 1; -fail: +free_e: + BN_free(e); +free_rsa: RSA_free(rsa); return ret; } diff --git a/oss_write.c b/oss_write.c index d4b76585..311a514d 100644 --- a/oss_write.c +++ b/oss_write.c @@ -57,7 +57,7 @@ static int get_oss_format(enum sample_format sf) case SF_S16_BE: return AFMT_S16_BE; case SF_U16_LE: return AFMT_U16_LE; case SF_U16_BE: return AFMT_U16_BE; - default: return AFMT_S16_LE; + default: return -E_BAD_SAMPLE_FORMAT; } } @@ -113,10 +113,14 @@ static int oss_init(struct writer_node *wn, unsigned sample_rate, if (ret < 0) goto err; /* set PCM format */ - sample_format = format = get_oss_format(sample_format); + ret = get_oss_format(sample_format); + if (ret < 0) + return ret; + sample_format = format = ret; ret = ioctl(powd->fd, SNDCTL_DSP_SETFMT, &format); if (ret < 0) { ret = -ERRNO_TO_PARA_ERROR(errno); + PARA_ERROR_LOG("could not set sample format\n"); goto err; } ret = -E_BAD_SAMPLE_FORMAT; diff --git a/server.c b/server.c index eee0a412..6370cefd 100644 --- a/server.c +++ b/server.c @@ -488,6 +488,13 @@ static void init_server_command_task(struct server_command_task *sct, .post_select = command_post_select, .context = sct, }, &sched); + /* + * Detect whether the abstract Unix domain socket space is supported, + * but do not create the socket. We check this once in server context + * so that the command handlers inherit this bit of information and + * don't need to check again. + */ + create_local_socket(NULL); return; err: PARA_EMERG_LOG("%s\n", para_strerror(-ret)); diff --git a/spxdec_filter.c b/spxdec_filter.c index 5aa78b44..7be817dd 100644 --- a/spxdec_filter.c +++ b/spxdec_filter.c @@ -48,6 +48,7 @@ #include #include "para.h" +#include "portable_io.h" #include "list.h" #include "sched.h" #include "buffer_tree.h" @@ -121,12 +122,6 @@ static int speexdec_init(struct filter_node *fn) return 1; } -#if !defined(__LITTLE_ENDIAN__) && ( defined(WORDS_BIGENDIAN) || defined(__BIG_ENDIAN__) ) -#define le_short(s) ((short) ((unsigned short) (s) << 8) | ((unsigned short) (s) >> 8)) -#else -#define le_short(s) ((short) (s)) -#endif - /** * Size of the output buffer. * @@ -178,7 +173,7 @@ static int speexdec_write_frames(int packet_no, samples = new_frame_size * psd->shi.channels; btr_output = para_malloc(2 * samples); for (i = 0; i < samples; i++) - btr_output[i] = le_short(output[i + skip_idx]); + btr_output[i] = read_u16(output + i + skip_idx); btr_add_output((char *)btr_output, samples * 2, btrn); } return 1; diff --git a/string.c b/string.c index 742eafdf..65d22408 100644 --- a/string.c +++ b/string.c @@ -113,9 +113,9 @@ __must_check __malloc char *para_strdup(const char *s) } /** - * Print a formated message to a dynamically allocated string. + * Print a formatted message to a dynamically allocated string. * - * \param result The formated string is returned here. + * \param result The formatted string is returned here. * \param fmt The format string. * \param ap Initialized list of arguments. * diff --git a/t/t0004-server.sh b/t/t0004-server.sh index 7e8ea820..03957464 100755 --- a/t/t0004-server.sh +++ b/t/t0004-server.sh @@ -83,7 +83,7 @@ test_require_executables "ssh-keygen" missing_executables="$result" if [[ -z "$missing_objects" && -z "$missing_executables" ]]; then - ssh-keygen -q -t rsa -b 2048 -N "" -f $privkey + ssh-keygen -q -t rsa -b 2048 -N "" -m PEM -f $privkey key_gen_result=$? read &>/dev/null < /dev/tcp/localhost/$port diff --git a/vss.c b/vss.c index 2cd0a163..73c72311 100644 --- a/vss.c +++ b/vss.c @@ -35,11 +35,6 @@ #include "fd.h" extern struct misc_meta_data *mmd; - -extern void dccp_send_init(struct sender *); -extern void http_send_init(struct sender *); -extern void udp_send_init(struct sender *); - extern const struct sender udp_sender, dccp_sender, http_sender; const struct sender * const senders[] = { &http_sender, &dccp_sender, &udp_sender, NULL}; @@ -946,6 +941,7 @@ static int recv_afs_msg(int afs_socket, int *fd, uint32_t *code, uint32_t *data) } #ifndef MAP_POPULATE +/** As of 2018, neither FreeBSD-11.2 nor NetBSD-8.0 have MAP_POPULATE. */ #define MAP_POPULATE 0 #endif diff --git a/web/about.in.html b/web/about.in.html index d91a2ad4..8395864a 100644 --- a/web/about.in.html +++ b/web/about.in.html @@ -17,7 +17,8 @@ systems. It is written in C and released under the GPLv2. Author: André Noll, -maan@tuebingen.mpg.de +maan@tuebingen.mpg.de, +Homepage: http://people.tuebingen.mpg.de/maan/
Comments and bug reports are welcome. Please provide the version of paraslash you are using and relevant parts of the logs. diff --git a/web/manual.md b/web/manual.md index 04c716a8..2c806614 100644 --- a/web/manual.md +++ b/web/manual.md @@ -446,7 +446,7 @@ following commands: Next, change to the "bar" account on client_host and generate the key pair with the commands - ssh-keygen -q -t rsa -b 2048 -N '' -f $key + ssh-keygen -q -t rsa -b 2048 -N '' -m PEM This generates the two files id_rsa and id_rsa.pub in ~/.ssh. Note that para_server won't accept keys shorter than 2048 bits. Moreover,