From 73eabece3365c1bb47bf6b009682219c4492fda5 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Sat, 11 Dec 2004 00:10:41 +0000 Subject: * add first part of zeroconf publisher * bump version to 0.7.1. * improve logging subsystem (introducing log levels) * remove verbose flag on cli * add new API pa_sample_format_to_string() * replace strtol() by usages of pa_atou() and pa_atoi() git-svn-id: file:///home/lennart/svn/public/pulseaudio/trunk@317 fefdeb5f-60dc-0310-8127-8f9354f1896f --- polyp/Makefile.am | 21 ++++- polyp/caps.c | 4 +- polyp/cli-command.c | 224 ++++++++++++++++++++------------------------- polyp/cli-command.h | 9 +- polyp/cli.c | 5 +- polyp/client.c | 6 +- polyp/client.h | 2 +- polyp/cmdline.c | 26 ++++-- polyp/conf-parser.c | 11 +-- polyp/daemon-conf.c | 77 +++++++++++++--- polyp/daemon-conf.h | 3 +- polyp/dumpmodules.c | 2 +- polyp/log.c | 74 +++++++++++++-- polyp/log.h | 27 +++++- polyp/main.c | 37 ++++---- polyp/memblockq.c | 4 +- polyp/modargs.c | 20 +--- polyp/module-combine.c | 8 +- polyp/module-defs.h.m4 | 11 ++- polyp/module-match.c | 15 ++- polyp/module-oss-mmap.c | 4 +- polyp/module-oss.c | 10 +- polyp/module-tunnel.c | 4 +- polyp/module-x11-bell.c | 4 +- polyp/module-x11-publish.c | 4 +- polyp/module.c | 8 +- polyp/namereg.c | 17 ++-- polyp/pid.c | 8 +- polyp/protocol-native.c | 6 +- polyp/sample.c | 13 ++- polyp/sample.h | 5 +- polyp/sink-input.c | 4 +- polyp/sink.c | 4 +- polyp/source-output.c | 6 ++ polyp/source.c | 4 +- polyp/util.c | 49 ++++++++-- polyp/util.h | 3 + 37 files changed, 460 insertions(+), 279 deletions(-) (limited to 'polyp') diff --git a/polyp/Makefile.am b/polyp/Makefile.am index 7338b9e6..83b5670a 100644 --- a/polyp/Makefile.am +++ b/polyp/Makefile.am @@ -156,7 +156,8 @@ SYMDEF_FILES= \ module-tunnel-sink-symdef.h \ module-tunnel-source-symdef.h \ module-null-sink-symdef.h \ - module-esound-sink-symdef.h + module-esound-sink-symdef.h \ + module-zeroconf-publish-symdef.h EXTRA_DIST+=$(SYMDEF_FILES) BUILT_SOURCES+=$(SYMDEF_FILES) @@ -596,6 +597,24 @@ module_alsa_source_la_LIBADD = $(AM_LIBADD) $(ASOUNDLIB_LIBS) libalsa-util.la module_alsa_source_la_CFLAGS = $(AM_CFLAGS) $(ASOUNDLIB_CFLAGS) endif +### HOWL modules +if HAVE_HOWL +modlib_LTLIBRARIES+= \ + libhowl-wrap.la \ + module-zeroconf-publish.la + +libhowl_wrap_la_SOURCES = howl-wrap.c howl-wrap.h +libhowl_wrap_la_LDFLAGS = -avoid-version +libhowl_wrap_la_LIBADD = $(AM_LIBADD) $(HOWL_LIBS) +libhowl_wrap_la_CFLAGS = $(AM_CFLAGS) $(HOWL_CFLAGS) + +module_zeroconf_publish_la_SOURCES = module-zeroconf-publish.c +module_zeroconf_publish_la_LDFLAGS = -module -avoid-version +module_zeroconf_publish_la_LIBADD = $(AM_LIBADD) $(HOWL_LIBS) libhowl-wrap.la +module_zeroconf_publish_la_CFLAGS = $(AM_CFLAGS) $(HOWL_CFLAGS) + +endif + ### GLIB 2.0 support if HAVE_GLIB20 diff --git a/polyp/caps.c b/polyp/caps.c index 93fca89f..01ed1519 100644 --- a/polyp/caps.c +++ b/polyp/caps.c @@ -45,7 +45,7 @@ void pa_drop_root(void) { if (uid == 0 || geteuid() != 0) return; - /* pa_log(__FILE__": dropping root rights.\n"); */ + pa_log_info(__FILE__": dropping root rights.\n"); #if defined(HAVE_SETRESUID) setresuid(uid, uid, uid); @@ -76,7 +76,7 @@ int pa_limit_caps(void) { if (cap_set_proc(caps) < 0) goto fail; -/* pa_log(__FILE__": dropped capabilities successfully.\n"); */ + pa_log_info(__FILE__": dropped capabilities successfully.\n"); r = 0; diff --git a/polyp/cli-command.c b/polyp/cli-command.c index 72e04bf8..0e8e09a5 100644 --- a/polyp/cli-command.c +++ b/polyp/cli-command.c @@ -48,45 +48,50 @@ #include "xmalloc.h" #include "sound-file-stream.h" #include "props.h" +#include "util.h" struct command { const char *name; - int (*proc) (struct pa_core *c, struct pa_tokenizer*t, struct pa_strbuf *buf, int *fail, int *verbose); + int (*proc) (struct pa_core *c, struct pa_tokenizer*t, struct pa_strbuf *buf, int *fail); const char *help; unsigned args; }; +#define INCLUDE_META ".include" +#define FAIL_META ".fail" +#define NOFAIL_META ".nofail" + /* Prototypes for all available commands */ -static int pa_cli_command_exit(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_help(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_modules(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_clients(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_sinks(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_sources(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_sink_inputs(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_source_outputs(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_stat(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_info(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_load(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_unload(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_sink_volume(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_sink_input_volume(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_sink_default(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_source_default(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_kill_client(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_kill_sink_input(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_kill_source_output(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_scache_play(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_scache_remove(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_scache_list(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_scache_load(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_scache_load_dir(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_play_file(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_autoload_list(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_autoload_add(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_autoload_remove(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_dump(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); -static int pa_cli_command_list_props(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose); +static int pa_cli_command_exit(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_help(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_modules(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_clients(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_sinks(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_sources(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_sink_inputs(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_source_outputs(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_stat(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_info(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_load(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_unload(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_sink_volume(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_sink_input_volume(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_sink_default(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_source_default(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_kill_client(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_kill_sink_input(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_kill_source_output(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_scache_play(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_scache_remove(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_scache_list(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_scache_load(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_scache_load_dir(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_play_file(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_autoload_list(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_autoload_add(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_autoload_remove(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_dump(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); +static int pa_cli_command_list_props(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail); /* A method table for all available commands */ @@ -134,22 +139,21 @@ static const char whitespace[] = " \t\n\r"; static const char linebreak[] = "\n\r"; static uint32_t parse_index(const char *n) { - long index; - char *x; - index = strtol(n, &x, 0); - if (!x || *x != 0 || index < 0) + uint32_t index; + + if (pa_atou(n, &index) < 0) return (uint32_t) PA_IDXSET_INVALID; - return (uint32_t) index; + return index; } -static int pa_cli_command_exit(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_exit(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { assert(c && c->mainloop && t); c->mainloop->quit(c->mainloop, 0); return 0; } -static int pa_cli_command_help(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_help(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const struct command*command; assert(c && t && buf); @@ -161,7 +165,7 @@ static int pa_cli_command_help(struct pa_core *c, struct pa_tokenizer *t, struct return 0; } -static int pa_cli_command_modules(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_modules(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { char *s; assert(c && t); s = pa_module_list_to_string(c); @@ -171,7 +175,7 @@ static int pa_cli_command_modules(struct pa_core *c, struct pa_tokenizer *t, str return 0; } -static int pa_cli_command_clients(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_clients(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { char *s; assert(c && t); s = pa_client_list_to_string(c); @@ -181,7 +185,7 @@ static int pa_cli_command_clients(struct pa_core *c, struct pa_tokenizer *t, str return 0; } -static int pa_cli_command_sinks(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_sinks(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { char *s; assert(c && t); s = pa_sink_list_to_string(c); @@ -191,7 +195,7 @@ static int pa_cli_command_sinks(struct pa_core *c, struct pa_tokenizer *t, struc return 0; } -static int pa_cli_command_sources(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_sources(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { char *s; assert(c && t); s = pa_source_list_to_string(c); @@ -201,7 +205,7 @@ static int pa_cli_command_sources(struct pa_core *c, struct pa_tokenizer *t, str return 0; } -static int pa_cli_command_sink_inputs(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_sink_inputs(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { char *s; assert(c && t); s = pa_sink_input_list_to_string(c); @@ -211,7 +215,7 @@ static int pa_cli_command_sink_inputs(struct pa_core *c, struct pa_tokenizer *t, return 0; } -static int pa_cli_command_source_outputs(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_source_outputs(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { char *s; assert(c && t); s = pa_source_output_list_to_string(c); @@ -221,7 +225,7 @@ static int pa_cli_command_source_outputs(struct pa_core *c, struct pa_tokenizer return 0; } -static int pa_cli_command_stat(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_stat(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { char s[256]; assert(c && t); @@ -249,24 +253,23 @@ static int pa_cli_command_stat(struct pa_core *c, struct pa_tokenizer *t, struct return 0; } -static int pa_cli_command_info(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_info(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { assert(c && t); - pa_cli_command_stat(c, t, buf, fail, verbose); - pa_cli_command_modules(c, t, buf, fail, verbose); - pa_cli_command_sinks(c, t, buf, fail, verbose); - pa_cli_command_sources(c, t, buf, fail, verbose); - pa_cli_command_clients(c, t, buf, fail, verbose); - pa_cli_command_sink_inputs(c, t, buf, fail, verbose); - pa_cli_command_source_outputs(c, t, buf, fail, verbose); - pa_cli_command_scache_list(c, t, buf, fail, verbose); - pa_cli_command_autoload_list(c, t, buf, fail, verbose); + pa_cli_command_stat(c, t, buf, fail); + pa_cli_command_modules(c, t, buf, fail); + pa_cli_command_sinks(c, t, buf, fail); + pa_cli_command_sources(c, t, buf, fail); + pa_cli_command_clients(c, t, buf, fail); + pa_cli_command_sink_inputs(c, t, buf, fail); + pa_cli_command_source_outputs(c, t, buf, fail); + pa_cli_command_scache_list(c, t, buf, fail); + pa_cli_command_autoload_list(c, t, buf, fail); return 0; } -static int pa_cli_command_load(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_load(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { struct pa_module *m; const char *name; - char txt[256]; assert(c && t); if (!(name = pa_tokenizer_get(t, 1))) { @@ -279,14 +282,10 @@ static int pa_cli_command_load(struct pa_core *c, struct pa_tokenizer *t, struct return -1; } - if (*verbose) { - snprintf(txt, sizeof(txt), "Module successfully loaded, index: %u.\n", m->index); - pa_strbuf_puts(buf, txt); - } return 0; } -static int pa_cli_command_unload(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_unload(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { struct pa_module *m; uint32_t index; const char *i; @@ -308,11 +307,10 @@ static int pa_cli_command_unload(struct pa_core *c, struct pa_tokenizer *t, stru return 0; } -static int pa_cli_command_sink_volume(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_sink_volume(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *n, *v; - char *x = NULL; struct pa_sink *sink; - long volume; + uint32_t volume; if (!(n = pa_tokenizer_get(t, 1))) { pa_strbuf_puts(buf, "You need to specify a sink either by its name or its index.\n"); @@ -324,8 +322,7 @@ static int pa_cli_command_sink_volume(struct pa_core *c, struct pa_tokenizer *t, return -1; } - volume = strtol(v, &x, 0); - if (!x || *x != 0 || volume < 0) { + if (pa_atou(v, &volume) < 0) { pa_strbuf_puts(buf, "Failed to parse volume.\n"); return -1; } @@ -339,12 +336,11 @@ static int pa_cli_command_sink_volume(struct pa_core *c, struct pa_tokenizer *t, return 0; } -static int pa_cli_command_sink_input_volume(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_sink_input_volume(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *n, *v; struct pa_sink_input *si; - long volume; + uint32_t volume; uint32_t index; - char *x; if (!(n = pa_tokenizer_get(t, 1))) { pa_strbuf_puts(buf, "You need to specify a sink input by its index.\n"); @@ -361,9 +357,7 @@ static int pa_cli_command_sink_input_volume(struct pa_core *c, struct pa_tokeniz return -1; } - x = NULL; - volume = strtol(v, &x, 0); - if (!x || *x != 0 || volume < 0) { + if (pa_atou(v, &volume) < 0) { pa_strbuf_puts(buf, "Failed to parse volume.\n"); return -1; } @@ -377,7 +371,7 @@ static int pa_cli_command_sink_input_volume(struct pa_core *c, struct pa_tokeniz return 0; } -static int pa_cli_command_sink_default(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_sink_default(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *n; assert(c && t); @@ -390,7 +384,7 @@ static int pa_cli_command_sink_default(struct pa_core *c, struct pa_tokenizer *t return 0; } -static int pa_cli_command_source_default(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_source_default(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *n; assert(c && t); @@ -403,7 +397,7 @@ static int pa_cli_command_source_default(struct pa_core *c, struct pa_tokenizer return 0; } -static int pa_cli_command_kill_client(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_kill_client(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *n; struct pa_client *client; uint32_t index; @@ -428,7 +422,7 @@ static int pa_cli_command_kill_client(struct pa_core *c, struct pa_tokenizer *t, return 0; } -static int pa_cli_command_kill_sink_input(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_kill_sink_input(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *n; struct pa_sink_input *sink_input; uint32_t index; @@ -453,7 +447,7 @@ static int pa_cli_command_kill_sink_input(struct pa_core *c, struct pa_tokenizer return 0; } -static int pa_cli_command_kill_source_output(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_kill_source_output(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *n; struct pa_source_output *source_output; uint32_t index; @@ -478,7 +472,7 @@ static int pa_cli_command_kill_source_output(struct pa_core *c, struct pa_tokeni return 0; } -static int pa_cli_command_scache_list(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_scache_list(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { char *s; assert(c && t); s = pa_scache_list_to_string(c); @@ -488,10 +482,10 @@ static int pa_cli_command_scache_list(struct pa_core *c, struct pa_tokenizer *t, return 0; } -static int pa_cli_command_scache_play(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_scache_play(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *n, *sink_name; struct pa_sink *sink; - assert(c && t && buf && fail && verbose); + assert(c && t && buf && fail); if (!(n = pa_tokenizer_get(t, 1)) || !(sink_name = pa_tokenizer_get(t, 2))) { pa_strbuf_puts(buf, "You need to specify a sample name and a sink name.\n"); @@ -511,9 +505,9 @@ static int pa_cli_command_scache_play(struct pa_core *c, struct pa_tokenizer *t, return 0; } -static int pa_cli_command_scache_remove(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_scache_remove(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *n; - assert(c && t && buf && fail && verbose); + assert(c && t && buf && fail); if (!(n = pa_tokenizer_get(t, 1))) { pa_strbuf_puts(buf, "You need to specify a sample name.\n"); @@ -528,10 +522,10 @@ static int pa_cli_command_scache_remove(struct pa_core *c, struct pa_tokenizer * return 0; } -static int pa_cli_command_scache_load(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_scache_load(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *fname, *n; int r; - assert(c && t && buf && fail && verbose); + assert(c && t && buf && fail); if (!(fname = pa_tokenizer_get(t, 2)) || !(n = pa_tokenizer_get(t, 1))) { pa_strbuf_puts(buf, "You need to specify a file name and a sample name.\n"); @@ -549,9 +543,9 @@ static int pa_cli_command_scache_load(struct pa_core *c, struct pa_tokenizer *t, return 0; } -static int pa_cli_command_scache_load_dir(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_scache_load_dir(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *pname; - assert(c && t && buf && fail && verbose); + assert(c && t && buf && fail); if (!(pname = pa_tokenizer_get(t, 1))) { pa_strbuf_puts(buf, "You need to specify a path name.\n"); @@ -566,10 +560,10 @@ static int pa_cli_command_scache_load_dir(struct pa_core *c, struct pa_tokenizer return 0; } -static int pa_cli_command_play_file(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_play_file(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *fname, *sink_name; struct pa_sink *sink; - assert(c && t && buf && fail && verbose); + assert(c && t && buf && fail); if (!(fname = pa_tokenizer_get(t, 1)) || !(sink_name = pa_tokenizer_get(t, 2))) { pa_strbuf_puts(buf, "You need to specify a file name and a sink name.\n"); @@ -585,9 +579,9 @@ static int pa_cli_command_play_file(struct pa_core *c, struct pa_tokenizer *t, s return pa_play_file(sink, fname, PA_VOLUME_NORM); } -static int pa_cli_command_autoload_add(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_autoload_add(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *a, *b; - assert(c && t && buf && fail && verbose); + assert(c && t && buf && fail); if (!(a = pa_tokenizer_get(t, 1)) || !(b = pa_tokenizer_get(t, 2))) { pa_strbuf_puts(buf, "You need to specify a device name, a filename or a module name and optionally module arguments\n"); @@ -599,9 +593,9 @@ static int pa_cli_command_autoload_add(struct pa_core *c, struct pa_tokenizer *t return 0; } -static int pa_cli_command_autoload_remove(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_autoload_remove(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { const char *name; - assert(c && t && buf && fail && verbose); + assert(c && t && buf && fail); if (!(name = pa_tokenizer_get(t, 1))) { pa_strbuf_puts(buf, "You need to specify a device name\n"); @@ -616,7 +610,7 @@ static int pa_cli_command_autoload_remove(struct pa_core *c, struct pa_tokenizer return 0; } -static int pa_cli_command_autoload_list(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_autoload_list(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { char *s; assert(c && t); s = pa_autoload_list_to_string(c); @@ -626,13 +620,13 @@ static int pa_cli_command_autoload_list(struct pa_core *c, struct pa_tokenizer * return 0; } -static int pa_cli_command_list_props(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_list_props(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { assert(c && t); pa_property_dump(c, buf); return 0; } -static int pa_cli_command_dump(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail, int *verbose) { +static int pa_cli_command_dump(struct pa_core *c, struct pa_tokenizer *t, struct pa_strbuf *buf, int *fail) { struct pa_module *m; struct pa_sink *s; int nl; @@ -724,7 +718,7 @@ static int pa_cli_command_dump(struct pa_core *c, struct pa_tokenizer *t, struct } -int pa_cli_command_execute_line(struct pa_core *c, const char *s, struct pa_strbuf *buf, int *fail, int *verbose) { +int pa_cli_command_execute_line(struct pa_core *c, const char *s, struct pa_strbuf *buf, int *fail) { const char *cs; cs = s+strspn(s, whitespace); @@ -732,28 +726,18 @@ int pa_cli_command_execute_line(struct pa_core *c, const char *s, struct pa_strb if (*cs == '#' || !*cs) return 0; else if (*cs == '.') { - static const char fail_meta[] = ".fail"; - static const char nofail_meta[] = ".nofail"; - static const char verbose_meta[] = ".verbose"; - static const char noverbose_meta[] = ".noverbose"; - - if (!strcmp(cs, verbose_meta)) - *verbose = 1; - else if (!strcmp(cs, noverbose_meta)) - *verbose = 0; - else if (!strcmp(cs, fail_meta)) + if (!strcmp(cs, FAIL_META)) *fail = 1; - else if (!strcmp(cs, nofail_meta)) + else if (!strcmp(cs, NOFAIL_META)) *fail = 0; else { size_t l; - static const char include_meta[] = ".include"; l = strcspn(cs, whitespace); - if (l == sizeof(include_meta)-1 && !strncmp(cs, include_meta, l)) { + if (l == sizeof(INCLUDE_META)-1 && !strncmp(cs, INCLUDE_META, l)) { const char *filename = cs+l+strspn(cs+l, whitespace); - if (pa_cli_command_execute_file(c, filename, buf, fail, verbose) < 0) + if (pa_cli_command_execute_file(c, filename, buf, fail) < 0) if (*fail) return -1; } else { pa_strbuf_printf(buf, "Invalid meta command: %s\n", cs); @@ -772,7 +756,7 @@ int pa_cli_command_execute_line(struct pa_core *c, const char *s, struct pa_strb int ret; struct pa_tokenizer *t = pa_tokenizer_new(cs, command->args); assert(t); - ret = command->proc(c, t, buf, fail, verbose); + ret = command->proc(c, t, buf, fail); pa_tokenizer_free(t); unknown = 0; @@ -792,7 +776,7 @@ int pa_cli_command_execute_line(struct pa_core *c, const char *s, struct pa_strb return 0; } -int pa_cli_command_execute_file(struct pa_core *c, const char *fn, struct pa_strbuf *buf, int *fail, int *verbose) { +int pa_cli_command_execute_file(struct pa_core *c, const char *fn, struct pa_strbuf *buf, int *fail) { char line[256]; FILE *f = NULL; int ret = -1; @@ -805,20 +789,14 @@ int pa_cli_command_execute_file(struct pa_core *c, const char *fn, struct pa_str goto fail; } - if (*verbose) - pa_strbuf_printf(buf, "Executing file: '%s'\n", fn); - while (fgets(line, sizeof(line), f)) { char *e = line + strcspn(line, linebreak); *e = 0; - if (pa_cli_command_execute_line(c, line, buf, fail, verbose) < 0 && *fail) + if (pa_cli_command_execute_line(c, line, buf, fail) < 0 && *fail) goto fail; } - if (*verbose) - pa_strbuf_printf(buf, "Executed file: '%s'\n", fn); - ret = 0; fail: @@ -828,16 +806,16 @@ fail: return ret; } -int pa_cli_command_execute(struct pa_core *c, const char *s, struct pa_strbuf *buf, int *fail, int *verbose) { +int pa_cli_command_execute(struct pa_core *c, const char *s, struct pa_strbuf *buf, int *fail) { const char *p; - assert(c && s && buf && fail && verbose); + assert(c && s && buf && fail); p = s; while (*p) { size_t l = strcspn(p, linebreak); char *line = pa_xstrndup(p, l); - if (pa_cli_command_execute_line(c, line, buf, fail, verbose) < 0&& *fail) { + if (pa_cli_command_execute_line(c, line, buf, fail) < 0&& *fail) { pa_xfree(line); return -1; } diff --git a/polyp/cli-command.h b/polyp/cli-command.h index 4887c55e..7af9d014 100644 --- a/polyp/cli-command.h +++ b/polyp/cli-command.h @@ -27,15 +27,14 @@ /* Execute a single CLI command. Write the results to the string * buffer *buf. If *fail is non-zero the function will return -1 when - * one or more of the executed commands failed. If *verbose is - * non-zero the command is executed verbosely. Both *verbose and *fail + * one or more of the executed commands failed. *fail * may be modified by the function call. */ -int pa_cli_command_execute_line(struct pa_core *c, const char *s, struct pa_strbuf *buf, int *fail, int *verbose); +int pa_cli_command_execute_line(struct pa_core *c, const char *s, struct pa_strbuf *buf, int *fail); /* Execute a whole file of CLI commands */ -int pa_cli_command_execute_file(struct pa_core *c, const char *fn, struct pa_strbuf *buf, int *fail, int *verbose); +int pa_cli_command_execute_file(struct pa_core *c, const char *fn, struct pa_strbuf *buf, int *fail); /* Split the specified string into lines and run pa_cli_command_execute_line() for each. */ -int pa_cli_command_execute(struct pa_core *c, const char *s, struct pa_strbuf *buf, int *fail, int *verbose); +int pa_cli_command_execute(struct pa_core *c, const char *s, struct pa_strbuf *buf, int *fail); #endif diff --git a/polyp/cli.c b/polyp/cli.c index 7780d03d..04fbb7e0 100644 --- a/polyp/cli.c +++ b/polyp/cli.c @@ -55,7 +55,7 @@ struct pa_cli { struct pa_client *client; - int fail, verbose, kill_requested, defer_kill; + int fail, kill_requested, defer_kill; }; static void line_callback(struct pa_ioline *line, const char *s, void *userdata); @@ -85,7 +85,6 @@ struct pa_cli* pa_cli_new(struct pa_core *core, struct pa_iochannel *io, struct pa_ioline_puts(c->line, "Welcome to polypaudio! Use \"help\" for usage information.\n"PROMPT); c->fail = c->kill_requested = c->defer_kill = 0; - c->verbose = 1; return c; } @@ -129,7 +128,7 @@ static void line_callback(struct pa_ioline *line, const char *s, void *userdata) buf = pa_strbuf_new(); assert(buf); c->defer_kill++; - pa_cli_command_execute_line(c->core, s, buf, &c->fail, &c->verbose); + pa_cli_command_execute_line(c->core, s, buf, &c->fail); c->defer_kill--; pa_ioline_puts(line, p = pa_strbuf_tostring_free(buf)); pa_xfree(p); diff --git a/polyp/client.c b/polyp/client.c index 22c7197a..40f5e385 100644 --- a/polyp/client.c +++ b/polyp/client.c @@ -50,7 +50,7 @@ struct pa_client *pa_client_new(struct pa_core *core, const char *protocol_name, r = pa_idxset_put(core->clients, c, &c->index); assert(c->index != PA_IDXSET_INVALID && r >= 0); - pa_log(__FILE__": created %u \"%s\"\n", c->index, c->name); + pa_log_info(__FILE__": created %u \"%s\"\n", c->index, c->name); pa_subscription_post(core, PA_SUBSCRIPTION_EVENT_CLIENT|PA_SUBSCRIPTION_EVENT_NEW, c->index); pa_core_check_quit(core); @@ -65,7 +65,7 @@ void pa_client_free(struct pa_client *c) { pa_core_check_quit(c->core); - pa_log(__FILE__": freed %u \"%s\"\n", c->index, c->name); + pa_log_info(__FILE__": freed %u \"%s\"\n", c->index, c->name); pa_subscription_post(c->core, PA_SUBSCRIPTION_EVENT_CLIENT|PA_SUBSCRIPTION_EVENT_REMOVE, c->index); pa_xfree(c->name); pa_xfree(c->protocol_name); @@ -76,7 +76,7 @@ void pa_client_free(struct pa_client *c) { void pa_client_kill(struct pa_client *c) { assert(c); if (!c->kill) { - pa_log(__FILE__": kill() operation not implemented for client %u\n", c->index); + pa_log_warn(__FILE__": kill() operation not implemented for client %u\n", c->index); return; } diff --git a/polyp/client.h b/polyp/client.h index 58c5ee31..324bb27c 100644 --- a/polyp/client.h +++ b/polyp/client.h @@ -35,7 +35,7 @@ struct pa_client { struct pa_module *owner; char *name; struct pa_core *core; - const char *protocol_name; + char *protocol_name; void (*kill)(struct pa_client *c); void *userdata; diff --git a/polyp/cmdline.c b/polyp/cmdline.c index a39f6ca6..0951725a 100644 --- a/polyp/cmdline.c +++ b/polyp/cmdline.c @@ -43,7 +43,7 @@ enum { ARG_DUMP_MODULES, ARG_DAEMONIZE, ARG_FAIL, - ARG_VERBOSE, + ARG_LOG_LEVEL, ARG_HIGH_PRIORITY, ARG_DISALLOW_MODULE_LOADING, ARG_EXIT_IDLE_TIME, @@ -67,7 +67,8 @@ static struct option long_options[] = { {"dump-modules", 0, 0, ARG_DUMP_MODULES}, {"daemonize", 2, 0, ARG_DAEMONIZE}, {"fail", 2, 0, ARG_FAIL}, - {"verbose", 2, 0, ARG_VERBOSE}, + {"verbose", 2, 0, ARG_LOG_LEVEL}, + {"log-level", 2, 0, ARG_LOG_LEVEL}, {"high-priority", 2, 0, ARG_HIGH_PRIORITY}, {"disallow-module-loading", 2, 0, ARG_DISALLOW_MODULE_LOADING}, {"exit-idle-time", 2, 0, ARG_EXIT_IDLE_TIME}, @@ -104,7 +105,6 @@ void pa_cmdline_help(const char *argv0) { "OPTIONS:\n" " -D, --daemonize[=BOOL] Daemonize after startup\n" " --fail[=BOOL] Quit when startup fails\n" - " --verbose[=BOOL] Be slightly more verbose\n" " --high-priority[=BOOL] Try to set high process priority\n" " (only available as root)\n" " --disallow-module-loading[=BOOL] Disallow module loading after startup\n" @@ -114,6 +114,8 @@ void pa_cmdline_help(const char *argv0) { " this time passed\n" " --scache-idle-time=SECS Unload autoloaded samples when idle and\n" " this time passed\n" + " --log-level[=LEVEL] Increase or set verbosity level\n" + " -v Increase the verbosity level\n" " --log-target={auto,syslog,stderr} Specify the log target\n" " -p, --dl-search-path=PATH Set the search path for dynamic shared\n" " objects (plugins)\n" @@ -143,7 +145,7 @@ int pa_cmdline_parse(struct pa_daemon_conf *conf, int argc, char *const argv [], if (conf->script_commands) pa_strbuf_puts(buf, conf->script_commands); - while ((c = getopt_long(argc, argv, "L:F:ChDnp:k", long_options, NULL)) != -1) { + while ((c = getopt_long(argc, argv, "L:F:ChDnp:kv", long_options, NULL)) != -1) { switch (c) { case ARG_HELP: case 'h': @@ -200,11 +202,19 @@ int pa_cmdline_parse(struct pa_daemon_conf *conf, int argc, char *const argv [], } break; - case ARG_VERBOSE: - if ((conf->verbose = optarg ? pa_parse_boolean(optarg) : 1) < 0) { - pa_log(__FILE__": --verbose expects boolean argument\n"); - goto fail; + case 'v': + case ARG_LOG_LEVEL: + + if (optarg) { + if (pa_daemon_conf_set_log_level(conf, optarg) < 0) { + pa_log(__FILE__": --log-level expects log level argument (either numeric in range 0..4 or one of debug, info, notice, warn, error).\n"); + goto fail; + } + } else { + if (conf->log_level < PA_LOG_LEVEL_MAX-1) + conf->log_level++; } + break; case ARG_HIGH_PRIORITY: diff --git a/polyp/conf-parser.c b/polyp/conf-parser.c index 35c4766e..b25508e2 100644 --- a/polyp/conf-parser.c +++ b/polyp/conf-parser.c @@ -135,17 +135,16 @@ finish: } int pa_config_parse_int(const char *filename, unsigned line, const char *lvalue, const char *rvalue, void *data, void *userdata) { - int *i = data, k; - char *x = NULL; + int *i = data; + int32_t k; assert(filename && lvalue && rvalue && data); - - k = strtol(rvalue, &x, 0); - if (!*rvalue || !x || *x) { + + if (pa_atoi(rvalue, &k) < 0) { pa_log(__FILE__": [%s:%u] Failed to parse numeric value: %s\n", filename, line, rvalue); return -1; } - *i = k; + *i = (int) k; return 0; } diff --git a/polyp/daemon-conf.c b/polyp/daemon-conf.c index 7753da6a..a6afd05a 100644 --- a/polyp/daemon-conf.c +++ b/polyp/daemon-conf.c @@ -53,7 +53,6 @@ static const struct pa_daemon_conf default_conf = { .cmd = PA_CMD_DAEMON, .daemonize = 0, .fail = 1, - .verbose = 0, .high_priority = 0, .disallow_module_loading = 0, .exit_idle_time = -1, @@ -64,6 +63,7 @@ static const struct pa_daemon_conf default_conf = { .dl_search_path = NULL, .default_script_file = NULL, .log_target = PA_LOG_SYSLOG, + .log_level = PA_LOG_NOTICE, .resample_method = PA_RESAMPLER_SRC_SINC_FASTEST, .config_file = NULL, .use_pid_file = 1 @@ -108,6 +108,31 @@ int pa_daemon_conf_set_log_target(struct pa_daemon_conf *c, const char *string) return 0; } +int pa_daemon_conf_set_log_level(struct pa_daemon_conf *c, const char *string) { + uint32_t u; + assert(c && string); + + if (pa_atou(string, &u) >= 0) { + if (u >= PA_LOG_LEVEL_MAX) + return -1; + + c->log_level = (enum pa_log_level) u; + } else if (pa_startswith(string, "debug")) + c->log_level = PA_LOG_DEBUG; + else if (pa_startswith(string, "info")) + c->log_level = PA_LOG_INFO; + else if (pa_startswith(string, "notice")) + c->log_level = PA_LOG_NOTICE; + else if (pa_startswith(string, "warn")) + c->log_level = PA_LOG_WARN; + else if (pa_startswith(string, "err")) + c->log_level = PA_LOG_ERROR; + else + return -1; + + return 0; +} + int pa_daemon_conf_set_resample_method(struct pa_daemon_conf *c, const char *string) { int m; assert(c && string); @@ -131,6 +156,18 @@ static int parse_log_target(const char *filename, unsigned line, const char *lva return 0; } +static int parse_log_level(const char *filename, unsigned line, const char *lvalue, const char *rvalue, void *data, void *userdata) { + struct pa_daemon_conf *c = data; + assert(filename && lvalue && rvalue && data); + + if (pa_daemon_conf_set_log_level(c, rvalue) < 0) { + pa_log(__FILE__": [%s:%u] Invalid log level '%s'.\n", filename, line, rvalue); + return -1; + } + + return 0; +} + static int parse_resample_method(const char *filename, unsigned line, const char *lvalue, const char *rvalue, void *data, void *userdata) { struct pa_daemon_conf *c = data; assert(filename && lvalue && rvalue && data); @@ -148,7 +185,6 @@ int pa_daemon_conf_load(struct pa_daemon_conf *c, const char *filename) { FILE *f = NULL; struct pa_config_item table[] = { - { "verbose", pa_config_parse_bool, NULL }, { "daemonize", pa_config_parse_bool, NULL }, { "fail", pa_config_parse_bool, NULL }, { "high-priority", pa_config_parse_bool, NULL }, @@ -159,24 +195,27 @@ int pa_daemon_conf_load(struct pa_daemon_conf *c, const char *filename) { { "dl-search-path", pa_config_parse_string, NULL }, { "default-script-file", pa_config_parse_string, NULL }, { "log-target", parse_log_target, NULL }, + { "log-level", parse_log_level, NULL }, + { "verbose", parse_log_level, NULL }, { "resample-method", parse_resample_method, NULL }, { "use-pid-file", pa_config_parse_bool, NULL }, { NULL, NULL, NULL }, }; - table[0].data = &c->verbose; - table[1].data = &c->daemonize; - table[2].data = &c->fail; - table[3].data = &c->high_priority; - table[4].data = &c->disallow_module_loading; - table[5].data = &c->exit_idle_time; - table[6].data = &c->module_idle_time; - table[7].data = &c->scache_idle_time; - table[8].data = &c->dl_search_path; - table[9].data = &c->default_script_file; + table[0].data = &c->daemonize; + table[1].data = &c->fail; + table[2].data = &c->high_priority; + table[3].data = &c->disallow_module_loading; + table[4].data = &c->exit_idle_time; + table[5].data = &c->module_idle_time; + table[6].data = &c->scache_idle_time; + table[7].data = &c->dl_search_path; + table[8].data = &c->default_script_file; + table[9].data = c; table[10].data = c; table[11].data = c; - table[12].data = &c->use_pid_file; + table[12].data = c; + table[13].data = &c->use_pid_file; pa_xfree(c->config_file); c->config_file = NULL; @@ -214,13 +253,22 @@ int pa_daemon_conf_env(struct pa_daemon_conf *c) { return 0; } +static const char* const log_level_to_string[] = { + [PA_LOG_DEBUG] = "debug", + [PA_LOG_INFO] = "info", + [PA_LOG_NOTICE] = "notice", + [PA_LOG_WARN] = "warning", + [PA_LOG_ERROR] = "error" +}; + char *pa_daemon_conf_dump(struct pa_daemon_conf *c) { struct pa_strbuf *s = pa_strbuf_new(); if (c->config_file) pa_strbuf_printf(s, "### Read from configuration file: %s ###\n", c->config_file); + + assert(c->log_level <= PA_LOG_LEVEL_MAX); - pa_strbuf_printf(s, "verbose = %i\n", !!c->verbose); pa_strbuf_printf(s, "daemonize = %i\n", !!c->daemonize); pa_strbuf_printf(s, "fail = %i\n", !!c->fail); pa_strbuf_printf(s, "high-priority = %i\n", !!c->high_priority); @@ -231,6 +279,7 @@ char *pa_daemon_conf_dump(struct pa_daemon_conf *c) { pa_strbuf_printf(s, "dl-search-path = %s\n", c->dl_search_path ? c->dl_search_path : ""); pa_strbuf_printf(s, "default-script-file = %s\n", c->default_script_file); pa_strbuf_printf(s, "log-target = %s\n", c->auto_log_target ? "auto" : (c->log_target == PA_LOG_SYSLOG ? "syslog" : "stderr")); + pa_strbuf_printf(s, "log-level = %s\n", log_level_to_string[c->log_level]); pa_strbuf_printf(s, "resample-method = %s\n", pa_resample_method_to_string(c->resample_method)); pa_strbuf_printf(s, "use-pid-file = %i\n", c->use_pid_file); diff --git a/polyp/daemon-conf.h b/polyp/daemon-conf.h index f163400f..30137e8b 100644 --- a/polyp/daemon-conf.h +++ b/polyp/daemon-conf.h @@ -40,7 +40,6 @@ struct pa_daemon_conf { enum pa_daemon_conf_cmd cmd; int daemonize, fail, - verbose, high_priority, disallow_module_loading, exit_idle_time, @@ -50,6 +49,7 @@ struct pa_daemon_conf { use_pid_file; char *script_commands, *dl_search_path, *default_script_file; enum pa_log_target log_target; + enum pa_log_level log_level; int resample_method; char *config_file; }; @@ -74,6 +74,7 @@ int pa_daemon_conf_env(struct pa_daemon_conf *c); /* Set these configuration variables in the structure by passing a string */ int pa_daemon_conf_set_log_target(struct pa_daemon_conf *c, const char *string); +int pa_daemon_conf_set_log_level(struct pa_daemon_conf *c, const char *string); int pa_daemon_conf_set_resample_method(struct pa_daemon_conf *c, const char *string); #endif diff --git a/polyp/dumpmodules.c b/polyp/dumpmodules.c index 1903fe00..1dc14edc 100644 --- a/polyp/dumpmodules.c +++ b/polyp/dumpmodules.c @@ -86,7 +86,7 @@ static int callback(const char *path, lt_ptr data) { e = path; if (strlen(e) > sizeof(PREFIX)-1 && !strncmp(e, PREFIX, sizeof(PREFIX)-1)) - show_info(e, path, c->verbose ? long_info : short_info); + show_info(e, path, c->log_level >= PA_LOG_INFO ? long_info : short_info); return 0; } diff --git a/polyp/log.c b/polyp/log.c index dc41dcd2..530fa691 100644 --- a/polyp/log.c +++ b/polyp/log.c @@ -34,7 +34,16 @@ static char *log_ident = NULL; static enum pa_log_target log_target = PA_LOG_STDERR; -static void (*user_log_func)(const char *s) = NULL; +static void (*user_log_func)(enum pa_log_level l, const char *s) = NULL; +static enum pa_log_level maximal_level = PA_LOG_NOTICE; + +static const int level_to_syslog[] = { + [PA_LOG_ERROR] = LOG_ERR, + [PA_LOG_WARN] = LOG_WARNING, + [PA_LOG_NOTICE] = LOG_NOTICE, + [PA_LOG_INFO] = LOG_INFO, + [PA_LOG_DEBUG] = LOG_DEBUG +}; void pa_log_set_ident(const char *p) { if (log_ident) @@ -43,34 +52,85 @@ void pa_log_set_ident(const char *p) { log_ident = pa_xstrdup(p); } -void pa_log_set_target(enum pa_log_target t, void (*func)(const char*s)) { +void pa_log_set_maximal_level(enum pa_log_level l) { + assert(l < PA_LOG_LEVEL_MAX); + maximal_level = l; +} + +void pa_log_set_target(enum pa_log_target t, void (*func)(enum pa_log_level l, const char*s)) { assert(t == PA_LOG_USER || !func); log_target = t; user_log_func = func; } -void pa_log(const char *format, ...) { - va_list ap; - va_start(ap, format); +void pa_log_levelv(enum pa_log_level level, const char *format, va_list ap) { + assert(level < PA_LOG_LEVEL_MAX); + if (level > maximal_level) + return; + switch (log_target) { case PA_LOG_STDERR: vfprintf(stderr, format, ap); break; + case PA_LOG_SYSLOG: openlog(log_ident ? log_ident : "???", LOG_PID, LOG_USER); - vsyslog(LOG_INFO, format, ap); + vsyslog(level_to_syslog[level], format, ap); closelog(); break; + case PA_LOG_USER: { char *t = pa_vsprintf_malloc(format, ap); assert(user_log_func); - user_log_func(t); + user_log_func(level, t); pa_xfree(t); } + case PA_LOG_NULL: break; } +} + +void pa_log_level(enum pa_log_level level, const char *format, ...) { + va_list ap; + va_start(ap, format); + pa_log_levelv(level, format, ap); + va_end(ap); +} + +void pa_log_debug(const char *format, ...) { + va_list ap; + va_start(ap, format); + pa_log_levelv(PA_LOG_DEBUG, format, ap); + va_end(ap); +} + +void pa_log_info(const char *format, ...) { + va_list ap; + va_start(ap, format); + pa_log_levelv(PA_LOG_INFO, format, ap); + va_end(ap); +} + +void pa_log_notice(const char *format, ...) { + va_list ap; + va_start(ap, format); + pa_log_levelv(PA_LOG_INFO, format, ap); + va_end(ap); +} + +void pa_log_warn(const char *format, ...) { + va_list ap; + va_start(ap, format); + pa_log_levelv(PA_LOG_WARN, format, ap); + va_end(ap); +} + +void pa_log_error(const char *format, ...) { + va_list ap; + va_start(ap, format); + pa_log_levelv(PA_LOG_ERROR, format, ap); va_end(ap); } diff --git a/polyp/log.h b/polyp/log.h index cf55386c..fe2dad59 100644 --- a/polyp/log.h +++ b/polyp/log.h @@ -22,6 +22,7 @@ USA. ***/ +#include #include "gcc-printf.h" /* A simple logging subsystem */ @@ -34,13 +35,35 @@ enum pa_log_target { PA_LOG_NULL /* to /dev/null */ }; +enum pa_log_level { + PA_LOG_ERROR = 0, /* Error messages */ + PA_LOG_WARN = 1, /* Warning messages */ + PA_LOG_NOTICE = 2, /* Notice messages */ + PA_LOG_INFO = 3, /* Info messages */ + PA_LOG_DEBUG = 4, /* debug message */ + PA_LOG_LEVEL_MAX +}; + /* Set an identifcation for the current daemon. Used when logging to syslog. */ void pa_log_set_ident(const char *p); /* Set another log target. If t is PA_LOG_USER you may specify a function that is called every log string */ -void pa_log_set_target(enum pa_log_target t, void (*func)(const char*s)); +void pa_log_set_target(enum pa_log_target t, void (*func)(enum pa_log_level, const char*s)); + +/* Minimal log level */ +void pa_log_set_maximal_level(enum pa_log_level l); /* Do a log line */ -void pa_log(const char *format, ...) PA_GCC_PRINTF_ATTR(1,2); +void pa_log_debug(const char *format, ...) PA_GCC_PRINTF_ATTR(1,2); +void pa_log_info(const char *format, ...) PA_GCC_PRINTF_ATTR(1,2); +void pa_log_notice(const char *format, ...) PA_GCC_PRINTF_ATTR(1,2); +void pa_log_warn(const char *format, ...) PA_GCC_PRINTF_ATTR(1,2); +void pa_log_error(const char *format, ...) PA_GCC_PRINTF_ATTR(1,2); + +void pa_log_level(enum pa_log_level level, const char *format, ...) PA_GCC_PRINTF_ATTR(2,3); + +void pa_log_levelv(enum pa_log_level level, const char *format, va_list ap); + +#define pa_log pa_log_error #endif diff --git a/polyp/main.c b/polyp/main.c index 0ba28e5a..f49232d4 100644 --- a/polyp/main.c +++ b/polyp/main.c @@ -64,7 +64,7 @@ int deny_severity = LOG_WARNING; #endif static void signal_callback(struct pa_mainloop_api*m, struct pa_signal_event *e, int sig, void *userdata) { - pa_log(__FILE__": Got signal %s.\n", pa_strsignal(sig)); + pa_log_info(__FILE__": Got signal %s.\n", pa_strsignal(sig)); switch (sig) { case SIGUSR1: @@ -108,7 +108,7 @@ static void signal_callback(struct pa_mainloop_api*m, struct pa_signal_event *e, default: return; } - pa_log(c); + pa_log_notice(c); pa_xfree(c); } @@ -118,7 +118,7 @@ static void signal_callback(struct pa_mainloop_api*m, struct pa_signal_event *e, case SIGINT: case SIGTERM: default: - pa_log(__FILE__": Exiting.\n"); + pa_log_info(__FILE__": Exiting.\n"); m->quit(m, 1); return; } @@ -150,7 +150,7 @@ int main(int argc, char *argv[]) { suid_root = getuid() != 0 && geteuid() == 0; if (suid_root && (pa_uid_in_group("realtime", &gid) <= 0 || gid >= 1000)) { - pa_log(__FILE__": WARNING: called SUID root, but not in group 'realtime'.\n"); + pa_log_warn(__FILE__": WARNING: called SUID root, but not in group 'realtime'.\n"); pa_drop_root(); } @@ -165,15 +165,16 @@ int main(int argc, char *argv[]) { if (pa_daemon_conf_load(conf, NULL) < 0) goto finish; - + if (pa_daemon_conf_env(conf) < 0) goto finish; - + if (pa_cmdline_parse(conf, argc, argv, &d) < 0) { pa_log(__FILE__": failed to parse command line.\n"); goto finish; } - + + pa_log_set_maximal_level(conf->log_level); pa_log_set_target(conf->auto_log_target ? PA_LOG_STDERR : conf->log_target, NULL); if (conf->high_priority && conf->cmd == PA_CMD_DAEMON) @@ -215,11 +216,9 @@ int main(int argc, char *argv[]) { pid_t pid; if (pa_pid_file_check_running(&pid) < 0) { - if (conf->verbose) - pa_log(__FILE__": daemon not running\n"); + pa_log_info(__FILE__": daemon not running\n"); } else { - if (conf->verbose) - pa_log(__FILE__": daemon running as PID %u\n", pid); + pa_log_info(__FILE__": daemon running as PID %u\n", pid); retval = 0; } @@ -268,8 +267,10 @@ int main(int argc, char *argv[]) { retval = 1; } - if (conf->verbose) - pa_log(__FILE__": daemon startup %s.\n", retval ? "failed" : "succeeded"); + if (retval) + pa_log(__FILE__": daemon startup failed .\n"); + else + pa_log_info(__FILE__": daemon startup successful.\n"); goto finish; } @@ -318,10 +319,10 @@ int main(int argc, char *argv[]) { buf = pa_strbuf_new(); assert(buf); if (conf->default_script_file) - r = pa_cli_command_execute_file(c, conf->default_script_file, buf, &conf->fail, &conf->verbose); + r = pa_cli_command_execute_file(c, conf->default_script_file, buf, &conf->fail); if (r >= 0) - r = pa_cli_command_execute(c, conf->script_commands, buf, &conf->fail, &conf->verbose); + r = pa_cli_command_execute(c, conf->script_commands, buf, &conf->fail); pa_log(s = pa_strbuf_tostring_free(buf)); pa_xfree(s); @@ -345,10 +346,10 @@ int main(int argc, char *argv[]) { c->scache_idle_time = conf->scache_idle_time; c->resample_method = conf->resample_method; - pa_log(__FILE__": Daemon startup complete.\n"); + pa_log_info(__FILE__": Daemon startup complete.\n"); if (pa_mainloop_run(mainloop, &retval) < 0) retval = 1; - pa_log(__FILE__": Daemon shutdown initiated.\n"); + pa_log_info(__FILE__": Daemon shutdown initiated.\n"); } pa_core_free(c); @@ -357,7 +358,7 @@ int main(int argc, char *argv[]) { pa_signal_done(); pa_mainloop_free(mainloop); - pa_log(__FILE__": Daemon terminated.\n"); + pa_log_info(__FILE__": Daemon terminated.\n"); finish: diff --git a/polyp/memblockq.c b/polyp/memblockq.c index 16c0da8e..3f2e4db1 100644 --- a/polyp/memblockq.c +++ b/polyp/memblockq.c @@ -58,7 +58,7 @@ struct pa_memblockq* pa_memblockq_new(size_t maxlength, size_t tlength, size_t b bq->current_length = 0; - /*pa_log(__FILE__": memblockq requested: maxlength=%u, tlength=%u, base=%u, prebuf=%u, minreq=%u\n", maxlength, tlength, base, prebuf, minreq);*/ + pa_log_debug(__FILE__": memblockq requested: maxlength=%u, tlength=%u, base=%u, prebuf=%u, minreq=%u\n", maxlength, tlength, base, prebuf, minreq); bq->base = base; @@ -83,7 +83,7 @@ struct pa_memblockq* pa_memblockq_new(size_t maxlength, size_t tlength, size_t b bq->orig_prebuf = bq->prebuf; - pa_log(__FILE__": memblockq sanitized: maxlength=%u, tlength=%u, base=%u, prebuf=%u, minreq=%u\n", bq->maxlength, bq->tlength, bq->base, bq->prebuf, bq->minreq); + pa_log_debug(__FILE__": memblockq sanitized: maxlength=%u, tlength=%u, base=%u, prebuf=%u, minreq=%u\n", bq->maxlength, bq->tlength, bq->base, bq->prebuf, bq->minreq); bq->mcalign = NULL; diff --git a/polyp/modargs.c b/polyp/modargs.c index 406f610f..9437d839 100644 --- a/polyp/modargs.c +++ b/polyp/modargs.c @@ -190,41 +190,27 @@ const char *pa_modargs_get_value(struct pa_modargs *ma, const char *key, const c int pa_modargs_get_value_u32(struct pa_modargs *ma, const char *key, uint32_t *value) { const char *v; - char *e; - unsigned long l; assert(ma && key && value); if (!(v = pa_modargs_get_value(ma, key, NULL))) return 0; - if (!*v) - return -1; - - l = strtoul(v, &e, 0); - if (*e) + if (pa_atou(v, value) < 0) return -1; - *value = (uint32_t) l; return 0; } int pa_modargs_get_value_s32(struct pa_modargs *ma, const char *key, int32_t *value) { const char *v; - char *e; - signed long l; assert(ma && key && value); if (!(v = pa_modargs_get_value(ma, key, NULL))) return 0; - if (!*v) + if (pa_atoi(v, value) < 0) return -1; - - l = strtol(v, &e, 0); - if (*e) - return -1; - - *value = (int32_t) l; + return 0; } diff --git a/polyp/module-combine.c b/polyp/module-combine.c index 95bd958f..7b3c26dd 100644 --- a/polyp/module-combine.c +++ b/polyp/module-combine.c @@ -111,7 +111,7 @@ static void adjust_rates(struct userdata *u) { target_latency = max_sink_latency > min_total_latency ? max_sink_latency : min_total_latency; - pa_log(__FILE__": [%s] target latency is %0.0f usec.\n", u->sink->name, (float) target_latency); + pa_log_info(__FILE__": [%s] target latency is %0.0f usec.\n", u->sink->name, (float) target_latency); base_rate = u->sink->sample_spec.rate; @@ -124,9 +124,9 @@ static void adjust_rates(struct userdata *u) { r += (uint32_t) (((((double) o->total_latency - target_latency))/u->adjust_time)*r/ 1000000); if (r < (uint32_t) (base_rate*0.9) || r > (uint32_t) (base_rate*1.1)) - pa_log(__FILE__": [%s] sample rates too different, not adjusting (%u vs. %u).\n", o->sink_input->name, base_rate, r); + pa_log_warn(__FILE__": [%s] sample rates too different, not adjusting (%u vs. %u).\n", o->sink_input->name, base_rate, r); else { - pa_log(__FILE__": [%s] new rate is %u Hz; ratio is %0.3f; latency is %0.0f usec.\n", o->sink_input->name, r, (double) r / base_rate, (float) o->total_latency); + pa_log_info(__FILE__": [%s] new rate is %u Hz; ratio is %0.3f; latency is %0.0f usec.\n", o->sink_input->name, r, (double) r / base_rate, (float) o->total_latency); pa_sink_input_set_rate(o->sink_input, r); } } @@ -358,7 +358,7 @@ int pa__init(struct pa_core *c, struct pa_module*m) { } if (u->n_outputs <= 1) - pa_log(__FILE__": WARNING: no slave sinks specified.\n"); + pa_log_warn(__FILE__": WARNING: no slave sinks specified.\n"); if (u->adjust_time > 0) { gettimeofday(&tv, NULL); diff --git a/polyp/module-defs.h.m4 b/polyp/module-defs.h.m4 index 85eb64a2..2b9cdf9e 100644 --- a/polyp/module-defs.h.m4 +++ b/polyp/module-defs.h.m4 @@ -1,13 +1,16 @@ dnl $Id$ changecom(`/*', `*/')dnl -define(`module', patsubst(patsubst(fname, `-symdef.h$'), `[^0-9a-zA-Z]', `_'))dnl -define(`c_symbol', patsubst(module, `[^0-9a-zA-Z]', `_'))dnl -define(`c_macro', patsubst(module, `[^0-9a-zA-Z]', `'))dnl +define(`module_name', patsubst(patsubst(fname, `-symdef.h$'), `[^0-9a-zA-Z]', `_'))dnl +define(`c_symbol', patsubst(module_name, `[^0-9a-zA-Z]', `_'))dnl +define(`c_macro', patsubst(module_name, `[^0-9a-zA-Z]', `'))dnl define(`incmacro', `foo'c_macro`symdeffoo')dnl -define(`gen_symbol', `#define $1 'module`_LTX_$1')dnl +define(`gen_symbol', `#define $1 'module_name`_LTX_$1')dnl #ifndef incmacro #define incmacro +#include "core.h" +#include "module.h" + gen_symbol(pa__init) gen_symbol(pa__done) gen_symbol(pa__get_author) diff --git a/polyp/module-match.c b/polyp/module-match.c index 6f4fc38c..7fdc5f3e 100644 --- a/polyp/module-match.c +++ b/polyp/module-match.c @@ -88,8 +88,9 @@ static int load_rules(struct userdata *u, const char *filename) { } while (!feof(f)) { - char *d, *v, *e = NULL; + char *d, *v; pa_volume_t volume; + uint32_t k; regex_t regex; char ln[256]; struct rule *rule; @@ -114,14 +115,14 @@ static int load_rules(struct userdata *u, const char *filename) { } *d = 0; - - volume = (pa_volume_t) strtol(v, &e, 0); - - if (!e || *e) { + if (pa_atou(v, &k) < 0) { pa_log(__FILE__": [%s:%u] failed to parse volume\n", filename, n); goto finish; } + volume = (pa_volume_t) k; + + if (regcomp(®ex, ln, REG_EXTENDED|REG_NOSUB) != 0) { pa_log(__FILE__": [%s:%u] invalid regular expression\n", filename, n); goto finish; @@ -162,10 +163,8 @@ static void callback(struct pa_core *c, enum pa_subscription_event_type t, uint3 if (t != (PA_SUBSCRIPTION_EVENT_SINK_INPUT|PA_SUBSCRIPTION_EVENT_NEW)) return; - if (!(si = pa_idxset_get_by_index(c->sink_inputs, index))) { - pa_log(__FILE__": WARNING: failed to get sink input\n"); + if (!(si = pa_idxset_get_by_index(c->sink_inputs, index))) return; - } if (!si->name) return; diff --git a/polyp/module-oss-mmap.c b/polyp/module-oss-mmap.c index 66daa77d..6fe4fa0c 100644 --- a/polyp/module-oss-mmap.c +++ b/polyp/module-oss-mmap.c @@ -289,7 +289,7 @@ int pa__init(struct pa_core *c, struct pa_module*m) { goto fail; } - pa_log(__FILE__": input -- %u fragments of size %u.\n", info.fragstotal, info.fragsize); + pa_log_info(__FILE__": input -- %u fragments of size %u.\n", info.fragstotal, info.fragsize); u->in_mmap_length = (u->in_fragment_size = info.fragsize) * (u->in_fragments = info.fragstotal); if ((u->in_mmap = mmap(NULL, u->in_mmap_length, PROT_READ, MAP_SHARED, u->fd, 0)) == MAP_FAILED) { @@ -320,7 +320,7 @@ int pa__init(struct pa_core *c, struct pa_module*m) { goto fail; } - pa_log(__FILE__": output -- %u fragments of size %u.\n", info.fragstotal, info.fragsize); + pa_log_info(__FILE__": output -- %u fragments of size %u.\n", info.fragstotal, info.fragsize); u->out_mmap_length = (u->out_fragment_size = info.fragsize) * (u->out_fragments = info.fragstotal); if ((u->out_mmap = mmap(NULL, u->out_mmap_length, PROT_WRITE, MAP_SHARED, u->fd, 0)) == MAP_FAILED) { diff --git a/polyp/module-oss.c b/polyp/module-oss.c index fe12b0bb..fa01876d 100644 --- a/polyp/module-oss.c +++ b/polyp/module-oss.c @@ -214,7 +214,7 @@ static pa_usec_t sink_get_latency_cb(struct pa_sink *s) { assert(s && u && u->sink); if (ioctl(u->fd, SNDCTL_DSP_GETODELAY, &arg) < 0) { - pa_log(__FILE__": device doesn't support SNDCTL_DSP_GETODELAY.\n"); + pa_log_info(__FILE__": device doesn't support SNDCTL_DSP_GETODELAY.\n"); s->get_latency = NULL; return 0; } @@ -230,7 +230,7 @@ static pa_usec_t sink_get_latency_cb(struct pa_sink *s) { static pa_usec_t source_get_latency_cb(struct pa_source *s) { struct userdata *u = s->userdata; audio_buf_info info; - assert(s && u && u->sink); + assert(s && u && u->source); if (!u->use_getispace) return 0; @@ -291,7 +291,7 @@ int pa__init(struct pa_core *c, struct pa_module*m) { if ((fd = pa_oss_open(p = pa_modargs_get_value(ma, "device", DEFAULT_DEVICE), &mode, NULL)) < 0) goto fail; - pa_log(__FILE__": device opened in %s mode.\n", mode == O_WRONLY ? "O_WRONLY" : (mode == O_RDONLY ? "O_RDONLY" : "O_RDWR")); + pa_log_info(__FILE__": device opened in %s mode.\n", mode == O_WRONLY ? "O_WRONLY" : (mode == O_RDONLY ? "O_RDONLY" : "O_RDWR")); if (nfrags >= 2 && frag_size >= 1) @@ -313,13 +313,13 @@ int pa__init(struct pa_core *c, struct pa_module*m) { u->use_getospace = u->use_getispace = 0; if (ioctl(fd, SNDCTL_DSP_GETISPACE, &info) >= 0) { - pa_log(__FILE__": input -- %u fragments of size %u.\n", info.fragstotal, info.fragsize); + pa_log_info(__FILE__": input -- %u fragments of size %u.\n", info.fragstotal, info.fragsize); in_frag_size = info.fragsize; u->use_getispace = 1; } if (ioctl(fd, SNDCTL_DSP_GETOSPACE, &info) >= 0) { - pa_log(__FILE__": output -- %u fragments of size %u.\n", info.fragstotal, info.fragsize); + pa_log_info(__FILE__": output -- %u fragments of size %u.\n", info.fragstotal, info.fragsize); out_frag_size = info.fragsize; u->use_getospace = 1; } diff --git a/polyp/module-tunnel.c b/polyp/module-tunnel.c index 39aaab57..d165aab8 100644 --- a/polyp/module-tunnel.c +++ b/polyp/module-tunnel.c @@ -545,7 +545,7 @@ static int load_key(struct userdata *u, const char*fn) { u->auth_cookie_in_property = 0; if (!fn && pa_authkey_prop_get(u->core, PA_NATIVE_COOKIE_PROPERTY_NAME, u->auth_cookie, sizeof(u->auth_cookie)) >= 0) { - pa_log(__FILE__": using already loaded auth cookie.\n"); + pa_log_debug(__FILE__": using already loaded auth cookie.\n"); pa_authkey_prop_ref(u->core, PA_NATIVE_COOKIE_PROPERTY_NAME); u->auth_cookie_in_property = 1; return 0; @@ -557,7 +557,7 @@ static int load_key(struct userdata *u, const char*fn) { if (pa_authkey_load_auto(fn, u->auth_cookie, sizeof(u->auth_cookie)) < 0) return -1; - pa_log(__FILE__": loading cookie from disk.\n"); + pa_log_debug(__FILE__": loading cookie from disk.\n"); if (pa_authkey_prop_put(u->core, PA_NATIVE_COOKIE_PROPERTY_NAME, u->auth_cookie, sizeof(u->auth_cookie)) >= 0) u->auth_cookie_in_property = 1; diff --git a/polyp/module-x11-bell.c b/polyp/module-x11-bell.c index c3987704..084f5d4b 100644 --- a/polyp/module-x11-bell.c +++ b/polyp/module-x11-bell.c @@ -69,7 +69,7 @@ static int ring_bell(struct userdata *u, int percent) { assert(u); if (!(s = pa_namereg_get(u->core, u->sink_name, PA_NAMEREG_SINK, 1))) { - pa_log(__FILE__": Invalid sink\n"); + pa_log(__FILE__": Invalid sink: %s\n", u->sink_name); return -1; } @@ -88,7 +88,7 @@ static int x11_event_callback(struct pa_x11_wrapper *w, XEvent *e, void *userdat bne = (XkbBellNotifyEvent*) e; if (ring_bell(u, bne->percent) < 0) { - pa_log(__FILE__": Ringing bell failed, reverting to X11 device bell.\n"); + pa_log_info(__FILE__": Ringing bell failed, reverting to X11 device bell.\n"); XkbForceDeviceBell(pa_x11_wrapper_get_display(w), bne->device, bne->bell_class, bne->bell_id, bne->percent); } diff --git a/polyp/module-x11-publish.c b/polyp/module-x11-publish.c index 598fe5b5..a47a7606 100644 --- a/polyp/module-x11-publish.c +++ b/polyp/module-x11-publish.c @@ -77,7 +77,7 @@ static int load_key(struct userdata *u, const char*fn) { u->auth_cookie_in_property = 0; if (!fn && pa_authkey_prop_get(u->core, PA_NATIVE_COOKIE_PROPERTY_NAME, u->auth_cookie, sizeof(u->auth_cookie)) >= 0) { - pa_log(__FILE__": using already loaded auth cookie.\n"); + pa_log_debug(__FILE__": using already loaded auth cookie.\n"); pa_authkey_prop_ref(u->core, PA_NATIVE_COOKIE_PROPERTY_NAME); u->auth_cookie_in_property = 1; return 0; @@ -89,7 +89,7 @@ static int load_key(struct userdata *u, const char*fn) { if (pa_authkey_load_auto(fn, u->auth_cookie, sizeof(u->auth_cookie)) < 0) return -1; - pa_log(__FILE__": loading cookie from disk.\n"); + pa_log_debug(__FILE__": loading cookie from disk.\n"); if (pa_authkey_prop_put(u->core, PA_NATIVE_COOKIE_PROPERTY_NAME, u->auth_cookie, sizeof(u->auth_cookie)) >= 0) u->auth_cookie_in_property = 1; diff --git a/polyp/module.c b/polyp/module.c index 67d7f44e..aedaae02 100644 --- a/polyp/module.c +++ b/polyp/module.c @@ -89,7 +89,7 @@ struct pa_module* pa_module_load(struct pa_core *c, const char *name, const char assert(m->init); if (m->init(c, m) < 0) { - pa_log(__FILE__": Failed to load module \"%s\" (argument: \"%s\"): initialization failed.\n", name, argument ? argument : ""); + pa_log_error(__FILE__": Failed to load module \"%s\" (argument: \"%s\"): initialization failed.\n", name, argument ? argument : ""); goto fail; } @@ -108,7 +108,7 @@ struct pa_module* pa_module_load(struct pa_core *c, const char *name, const char r = pa_idxset_put(c->modules, m, &m->index); assert(r >= 0 && m->index != PA_IDXSET_INVALID); - pa_log(__FILE__": Loaded \"%s\" (index: #%u; argument: \"%s\").\n", m->name, m->index, m->argument ? m->argument : ""); + pa_log_info(__FILE__": Loaded \"%s\" (index: #%u; argument: \"%s\").\n", m->name, m->index, m->argument ? m->argument : ""); pa_subscription_post(c, PA_SUBSCRIPTION_EVENT_MODULE|PA_SUBSCRIPTION_EVENT_NEW, m->index); @@ -135,13 +135,13 @@ static void pa_module_free(struct pa_module *m) { if (m->core->disallow_module_loading) return; - pa_log(__FILE__": Unloading \"%s\" (index: #%u).\n", m->name, m->index); + pa_log_info(__FILE__": Unloading \"%s\" (index: #%u).\n", m->name, m->index); m->done(m->core, m); lt_dlclose(m->dl); - pa_log(__FILE__": Unloaded \"%s\" (index: #%u).\n", m->name, m->index); + pa_log_info(__FILE__": Unloaded \"%s\" (index: #%u).\n", m->name, m->index); pa_subscription_post(m->core, PA_SUBSCRIPTION_EVENT_MODULE|PA_SUBSCRIPTION_EVENT_REMOVE, m->index); diff --git a/polyp/namereg.c b/polyp/namereg.c index dce8693f..04601442 100644 --- a/polyp/namereg.c +++ b/polyp/namereg.c @@ -35,6 +35,7 @@ #include "sink.h" #include "xmalloc.h" #include "subscribe.h" +#include "util.h" struct namereg_entry { enum pa_namereg_type type; @@ -112,8 +113,6 @@ void pa_namereg_unregister(struct pa_core *c, const char *name) { void* pa_namereg_get(struct pa_core *c, const char *name, enum pa_namereg_type type, int autoload) { struct namereg_entry *e; uint32_t index; - char *x = NULL; - void *d = NULL; assert(c); if (!name) { @@ -130,9 +129,7 @@ void* pa_namereg_get(struct pa_core *c, const char *name, enum pa_namereg_type t if (e->type == e->type) return e->data; - index = (uint32_t) strtol(name, &x, 0); - - if (!x || *x != 0) { + if (pa_atou(name, &index) < 0) { if (autoload) { pa_autoload_request(c, name, type); @@ -146,13 +143,13 @@ void* pa_namereg_get(struct pa_core *c, const char *name, enum pa_namereg_type t } if (type == PA_NAMEREG_SINK) - d = pa_idxset_get_by_index(c->sinks, index); + return pa_idxset_get_by_index(c->sinks, index); else if (type == PA_NAMEREG_SOURCE) - d = pa_idxset_get_by_index(c->sources, index); + return pa_idxset_get_by_index(c->sources, index); else if (type == PA_NAMEREG_SAMPLE && c->scache) - d = pa_idxset_get_by_index(c->scache, index); - - return d; + return pa_idxset_get_by_index(c->scache, index); + + return NULL; } void pa_namereg_set_default(struct pa_core*c, const char *name, enum pa_namereg_type type) { diff --git a/polyp/pid.c b/polyp/pid.c index 32365136..2fac687e 100644 --- a/polyp/pid.c +++ b/polyp/pid.c @@ -43,8 +43,8 @@ * pid could be read, return 0, on failure (pid_t) -1 */ static pid_t read_pid(const char *fn, int fd) { ssize_t r; - char t[20], *e = NULL; - long int pid; + char t[20], *e; + uint32_t pid; assert(fn && fd >= 0); @@ -57,8 +57,10 @@ static pid_t read_pid(const char *fn, int fd) { return (pid_t) 0; t[r] = 0; + if ((e = strchr(t, '\n'))) + *e = 0; - if (!t[0] || (pid = strtol(t, &e, 0)) == 0 || (*e != 0 && *e != '\n')) { + if (pa_atou(t, &pid) < 0) { pa_log(__FILE__": WARNING: failed to parse PID file '%s'\n", fn); return (pid_t) -1; } diff --git a/polyp/protocol-native.c b/polyp/protocol-native.c index 84d4efe8..94dc5e5f 100644 --- a/polyp/protocol-native.c +++ b/polyp/protocol-native.c @@ -2003,7 +2003,7 @@ static void on_connection(struct pa_socket_server*s, struct pa_iochannel *io, vo assert(io && p); if (pa_idxset_ncontents(p->connections)+1 > MAX_CONNECTIONS) { - pa_log(__FILE__": Warning! Too many connections (%u), dropping incoming connection.\n", MAX_CONNECTIONS); + pa_log_warn(__FILE__": Warning! Too many connections (%u), dropping incoming connection.\n", MAX_CONNECTIONS); pa_iochannel_free(io); return; } @@ -2057,7 +2057,7 @@ static int load_key(struct pa_protocol_native*p, const char*fn) { p->auth_cookie_in_property = 0; if (!fn && pa_authkey_prop_get(p->core, PA_NATIVE_COOKIE_PROPERTY_NAME, p->auth_cookie, sizeof(p->auth_cookie)) >= 0) { - pa_log(__FILE__": using already loaded auth cookie.\n"); + pa_log_info(__FILE__": using already loaded auth cookie.\n"); pa_authkey_prop_ref(p->core, PA_NATIVE_COOKIE_PROPERTY_NAME); p->auth_cookie_in_property = 1; return 0; @@ -2069,7 +2069,7 @@ static int load_key(struct pa_protocol_native*p, const char*fn) { if (pa_authkey_load_auto(fn, p->auth_cookie, sizeof(p->auth_cookie)) < 0) return -1; - pa_log(__FILE__": loading cookie from disk.\n"); + pa_log_info(__FILE__": loading cookie from disk.\n"); if (pa_authkey_prop_put(p->core, PA_NATIVE_COOKIE_PROPERTY_NAME, p->auth_cookie, sizeof(p->auth_cookie)) >= 0) p->auth_cookie_in_property = 1; diff --git a/polyp/sample.c b/polyp/sample.c index 978a3d6a..b0723f70 100644 --- a/polyp/sample.c +++ b/polyp/sample.c @@ -84,7 +84,7 @@ int pa_sample_spec_equal(const struct pa_sample_spec*a, const struct pa_sample_s return (a->format == b->format) && (a->rate == b->rate) && (a->channels == b->channels); } -void pa_sample_spec_snprint(char *s, size_t l, const struct pa_sample_spec *spec) { +const char *pa_sample_format_to_string(enum pa_sample_format f) { static const char* const table[]= { [PA_SAMPLE_U8] = "U8", [PA_SAMPLE_ALAW] = "ALAW", @@ -95,12 +95,21 @@ void pa_sample_spec_snprint(char *s, size_t l, const struct pa_sample_spec *spec [PA_SAMPLE_FLOAT32BE] = "FLOAT32BE", }; + if (f >= PA_SAMPLE_MAX) + return NULL; + + return table[f]; +} + +void pa_sample_spec_snprint(char *s, size_t l, const struct pa_sample_spec *spec) { + assert(s && l && spec); + if (!pa_sample_spec_valid(spec)) { snprintf(s, l, "Invalid"); return; } - snprintf(s, l, "%s %uch %uHz", table[spec->format], spec->channels, spec->rate); + snprintf(s, l, "%s %uch %uHz", pa_sample_format_to_string(spec->format), spec->channels, spec->rate); } pa_volume_t pa_volume_multiply(pa_volume_t a, pa_volume_t b) { diff --git a/polyp/sample.h b/polyp/sample.h index 93025a10..59226c46 100644 --- a/polyp/sample.h +++ b/polyp/sample.h @@ -86,6 +86,9 @@ int pa_sample_spec_valid(const struct pa_sample_spec *spec); /** Return non-zero when the two sample type specifications match */ int pa_sample_spec_equal(const struct pa_sample_spec*a, const struct pa_sample_spec*b); +/* Return a descriptive string for the specified sample format. \since 0.7.1 */ +const char *pa_sample_format_to_string(enum pa_sample_format f); + /** Maximum required string length for pa_sample_spec_snprint() */ #define PA_SAMPLE_SPEC_SNPRINT_MAX 32 @@ -126,7 +129,7 @@ pa_volume_t pa_volume_from_user(double v); /** Pretty print a byte size value. (i.e. "2.5 MB") */ void pa_bytes_snprint(char *s, size_t l, unsigned v); -/** Parse a sample format text */ +/** Parse a sample format text. Inverse of pa_sample_format_to_string() */ enum pa_sample_format pa_parse_sample_format(const char *format); PA_C_DECL_END diff --git a/polyp/sink-input.c b/polyp/sink-input.c index e66278ed..347b8f5c 100644 --- a/polyp/sink-input.c +++ b/polyp/sink-input.c @@ -85,7 +85,7 @@ struct pa_sink_input* pa_sink_input_new(struct pa_sink *s, const char *name, con assert(r == 0); pa_sample_spec_snprint(st, sizeof(st), spec); - pa_log(__FILE__": created %u \"%s\" on %u with sample spec \"%s\"\n", i->index, i->name, s->index, st); + pa_log_info(__FILE__": created %u \"%s\" on %u with sample spec \"%s\"\n", i->index, i->name, s->index, st); pa_subscription_post(s->core, PA_SUBSCRIPTION_EVENT_SINK_INPUT|PA_SUBSCRIPTION_EVENT_NEW, i->index); @@ -115,6 +115,8 @@ static void sink_input_free(struct pa_sink_input* i) { if (i->state != PA_SINK_INPUT_DISCONNECTED) pa_sink_input_disconnect(i); + pa_log_info(__FILE__": freed %u \"%s\"\n", i->index, i->name); + if (i->resampled_chunk.memblock) pa_memblock_unref(i->resampled_chunk.memblock); if (i->resampler) diff --git a/polyp/sink.c b/polyp/sink.c index 29aef6fb..3d20884b 100644 --- a/polyp/sink.c +++ b/polyp/sink.c @@ -81,7 +81,7 @@ struct pa_sink* pa_sink_new(struct pa_core *core, const char *name, int fail, co assert(s->index != PA_IDXSET_INVALID && r >= 0); pa_sample_spec_snprint(st, sizeof(st), spec); - pa_log(__FILE__": created %u \"%s\" with sample spec \"%s\"\n", s->index, s->name, st); + pa_log_info(__FILE__": created %u \"%s\" with sample spec \"%s\"\n", s->index, s->name, st); pa_subscription_post(core, PA_SUBSCRIPTION_EVENT_SINK | PA_SUBSCRIPTION_EVENT_NEW, s->index); @@ -117,7 +117,7 @@ static void sink_free(struct pa_sink *s) { if (s->state != PA_SINK_DISCONNECTED) pa_sink_disconnect(s); - pa_log(__FILE__": freed %u \"%s\"\n", s->index, s->name); + pa_log_info(__FILE__": freed %u \"%s\"\n", s->index, s->name); pa_source_unref(s->monitor_source); s->monitor_source = NULL; diff --git a/polyp/source-output.c b/polyp/source-output.c index fb06ff8f..3568fd6f 100644 --- a/polyp/source-output.c +++ b/polyp/source-output.c @@ -37,6 +37,7 @@ struct pa_source_output* pa_source_output_new(struct pa_source *s, const char *n struct pa_source_output *o; struct pa_resampler *resampler = NULL; int r; + char st[256]; assert(s && spec); if (pa_idxset_ncontents(s->outputs) >= PA_MAX_OUTPUTS_PER_SOURCE) { @@ -73,6 +74,9 @@ struct pa_source_output* pa_source_output_new(struct pa_source *s, const char *n r = pa_idxset_put(s->outputs, o, NULL); assert(r == 0); + pa_sample_spec_snprint(st, sizeof(st), spec); + pa_log_info(__FILE__": created %u \"%s\" on %u with sample spec \"%s\"\n", o->index, o->name, s->index, st); + pa_subscription_post(s->core, PA_SUBSCRIPTION_EVENT_SOURCE_OUTPUT|PA_SUBSCRIPTION_EVENT_NEW, o->index); return o; @@ -100,6 +104,8 @@ static void source_output_free(struct pa_source_output* o) { if (o->state != PA_SOURCE_OUTPUT_DISCONNECTED) pa_source_output_disconnect(o); + pa_log_info(__FILE__": freed %u \"%s\"\n", o->index, o->name); + if (o->resampler) pa_resampler_free(o->resampler); diff --git a/polyp/source.c b/polyp/source.c index 026ec7a8..7cdb9117 100644 --- a/polyp/source.c +++ b/polyp/source.c @@ -68,7 +68,7 @@ struct pa_source* pa_source_new(struct pa_core *core, const char *name, int fail assert(s->index != PA_IDXSET_INVALID && r >= 0); pa_sample_spec_snprint(st, sizeof(st), spec); - pa_log(__FILE__": created %u \"%s\" with sample spec \"%s\"\n", s->index, s->name, st); + pa_log_info(__FILE__": created %u \"%s\" with sample spec \"%s\"\n", s->index, s->name, st); pa_subscription_post(core, PA_SUBSCRIPTION_EVENT_SOURCE | PA_SUBSCRIPTION_EVENT_NEW, s->index); @@ -101,7 +101,7 @@ static void source_free(struct pa_source *s) { if (s->state != PA_SOURCE_DISCONNECTED) pa_source_disconnect(s); - pa_log(__FILE__": freed %u \"%s\"\n", s->index, s->name); + pa_log_info(__FILE__": freed %u \"%s\"\n", s->index, s->name); pa_idxset_free(s->outputs, NULL, NULL); diff --git a/polyp/util.c b/polyp/util.c index 970ebb93..ff1aebf3 100644 --- a/polyp/util.c +++ b/polyp/util.c @@ -381,9 +381,9 @@ supported.*/ void pa_raise_priority(void) { if (setpriority(PRIO_PROCESS, 0, NICE_LEVEL) < 0) - pa_log(__FILE__": setpriority() failed: %s\n", strerror(errno)); -/* else */ -/* pa_log(__FILE__": Successfully gained nice level %i.\n", NICE_LEVEL); */ + pa_log_warn(__FILE__": setpriority() failed: %s\n", strerror(errno)); + else + pa_log_info(__FILE__": Successfully gained nice level %i.\n", NICE_LEVEL); #ifdef _POSIX_PRIORITY_SCHEDULING { @@ -396,11 +396,11 @@ void pa_raise_priority(void) { sp.sched_priority = 1; if (sched_setscheduler(0, SCHED_FIFO, &sp) < 0) { - pa_log(__FILE__": sched_setscheduler() failed: %s\n", strerror(errno)); + pa_log_warn(__FILE__": sched_setscheduler() failed: %s\n", strerror(errno)); return; } -/* pa_log(__FILE__": Successfully enabled SCHED_FIFO scheduling.\n"); */ + pa_log_info(__FILE__": Successfully enabled SCHED_FIFO scheduling.\n"); } #endif } @@ -698,17 +698,17 @@ int pa_unlock_lockfile(const char *fn, int fd) { assert(fn && fd >= 0); if (unlink(fn) < 0) { - pa_log(__FILE__": WARNING: unable to remove lock file '%s': %s\n", fn, strerror(errno)); + pa_log_warn(__FILE__": WARNING: unable to remove lock file '%s': %s\n", fn, strerror(errno)); r = -1; } if (pa_lock_fd(fd, 0) < 0) { - pa_log(__FILE__": WARNING: failed to unlock file '%s'.\n", fn); + pa_log_warn(__FILE__": WARNING: failed to unlock file '%s'.\n", fn); r = -1; } if (close(fd) < 0) { - pa_log(__FILE__": WARNING: failed to close lock file '%s': %s\n", fn, strerror(errno)); + pa_log_warn(__FILE__": WARNING: failed to close lock file '%s': %s\n", fn, strerror(errno)); r = -1; } @@ -862,6 +862,7 @@ char *pa_runtime_path(const char *fn, char *s, size_t l) { return s; } +/* Wait t milliseconds */ int pa_msleep(unsigned long t) { struct timespec ts; @@ -870,3 +871,35 @@ int pa_msleep(unsigned long t) { return nanosleep(&ts, NULL); } + +/* Convert the string s to a signed integer in *ret_i */ +int pa_atoi(const char *s, int32_t *ret_i) { + char *x = NULL; + long l; + assert(s && ret_i); + + l = strtol(s, &x, 0); + + if (x || *x) + return -1; + + *ret_i = (int32_t) l; + + return 0; +} + +/* Convert the string s to an unsigned integer in *ret_u */ +int pa_atou(const char *s, uint32_t *ret_u) { + char *x = NULL; + unsigned long l; + assert(s && ret_u); + + l = strtoul(s, &x, 0); + + if (!x || *x) + return -1; + + *ret_u = (uint32_t) l; + + return 0; +} diff --git a/polyp/util.h b/polyp/util.h index 922aa49e..2cfc5f6e 100644 --- a/polyp/util.h +++ b/polyp/util.h @@ -90,4 +90,7 @@ char *pa_runtime_path(const char *fn, char *s, size_t l); int pa_msleep(unsigned long t); +int pa_atoi(const char *s, int32_t *ret_i); +int pa_atou(const char *s, uint32_t *ret_u); + #endif -- cgit