From a193eb24f5257d8f76a3c12d5c7a16297f3448dd Mon Sep 17 00:00:00 2001 From: Mike Brady <4265913+mikebrady@users.noreply.github.com> Date: Wed, 5 Oct 2022 10:00:27 +0100 Subject: [PATCH 1/2] Add names of AP2 clients to debug messages. --- rtsp.c | 55 ++++++++++++++++++++++++++++++++++++++----------------- 1 file changed, 38 insertions(+), 17 deletions(-) diff --git a/rtsp.c b/rtsp.c index d61ffeb1..76395df9 100644 --- a/rtsp.c +++ b/rtsp.c @@ -1275,7 +1275,9 @@ void clear_ptp_clock() { ssize_t read_from_rtsp_connection(rtsp_conn_info *conn, void *buf, size_t count) { // first try to read with a timeout, to see if there is any traffic... - ssize_t response = timed_read_from_rtsp_connection(conn, 10000000000L, buf, count); + // ssize_t response = timed_read_from_rtsp_connection(conn, 20000000000L, buf, count); + // actually don't use a timeout -- OwnTone doesn't supply regular traffic. + ssize_t response = timed_read_from_rtsp_connection(conn, 0, buf, count); if ((response == -1) && ((errno == EAGAIN) || (errno == EWOULDBLOCK))) { if (conn->rtsp_link_is_idle == 0) { debug(1, "Connection %d: RTSP connection is idle.", conn->connection_number); @@ -1622,7 +1624,7 @@ void handle_record(rtsp_conn_info *conn, rtsp_message *req, rtsp_message *resp) if (conn->player_thread) warn("Connection %d: RECORD: Duplicate RECORD message -- ignored", conn->connection_number); else { - debug(1, "Connection %d: AP1 ALAC Stream, from %s:%u to self at %s:%u.", + debug(1, "Connection %d: Classic AirPlay connection from %s:%u to self at %s:%u.", conn->connection_number, conn->client_ip_string, conn->client_rtsp_port, conn->self_ip_string, conn->self_rtsp_port); activity_monitor_signify_activity(1); @@ -2830,6 +2832,15 @@ void handle_setup_2(rtsp_conn_info *conn, rtsp_message *req, rtsp_message *resp) plist_t messagePlist = plist_from_rtsp_content(req); plist_t setupResponsePlist = plist_new_dict(); resp->respcode = 400; + + // see if we can get a name for the client + char *clientNameString = NULL; + plist_t nameItem = plist_dict_get_item(messagePlist, "name"); + if (nameItem != NULL) { + plist_get_string_val(nameItem, &clientNameString); + } else { + clientNameString = strdup(""); + } // see if the incoming plist contains a "streams" array plist_t streams = plist_dict_get_item(messagePlist, "streams"); @@ -2847,8 +2858,8 @@ void handle_setup_2(rtsp_conn_info *conn, rtsp_message *req, rtsp_message *resp) plist_get_string_val(timingProtocol, &timingProtocolString); if (timingProtocolString) { if (strcmp(timingProtocolString, "PTP") == 0) { - debug(2, "Connection %d: AP2 PTP connection from %s:%u to self at %s:%u.", - conn->connection_number, conn->client_ip_string, conn->client_rtsp_port, + debug(1, "Connection %d: AP2 PTP connection from %s:%u (\"%s\") to self at %s:%u.", + conn->connection_number, conn->client_ip_string, conn->client_rtsp_port, clientNameString, conn->self_ip_string, conn->self_rtsp_port); conn->airplay_stream_category = ptp_stream; conn->timing_type = ts_ptp; @@ -2862,20 +2873,24 @@ void handle_setup_2(rtsp_conn_info *conn, rtsp_message *req, rtsp_message *resp) send_ssnc_metadata('svip', conn->self_ip_string, strlen(conn->self_ip_string), 1); #endif } else if (strcmp(timingProtocolString, "NTP") == 0) { - debug(1, "Connection %d: SETUP: NTP setup detected.", conn->connection_number); + debug(1, "Connection %d: SETUP: NTP setup from %s:%u (\"%s\") to self at %s:%u.", + conn->connection_number, conn->client_ip_string, conn->client_rtsp_port, clientNameString, + conn->self_ip_string, conn->self_rtsp_port); conn->airplay_stream_category = ntp_stream; conn->timing_type = ts_ntp; } else if (strcmp(timingProtocolString, "None") == 0) { - debug(2, "Connection %d: SETUP: a \"None\" setup detected.", conn->connection_number); + debug(3, "Connection %d: SETUP: a \"None\" setup detected from %s:%u (\"%s\") to self at %s:%u.", + conn->connection_number, conn->client_ip_string, conn->client_rtsp_port, clientNameString, + conn->self_ip_string, conn->self_rtsp_port); // now check to see if it's got the "isRemoteControlOnly" item and check it's true plist_t isRemoteControlOnly = plist_dict_get_item(messagePlist, "isRemoteControlOnly"); if (isRemoteControlOnly != NULL) { uint8_t isRemoteControlOnlyBoolean = 0; plist_get_bool_val(isRemoteControlOnly, &isRemoteControlOnlyBoolean); if (isRemoteControlOnlyBoolean != 0) { - debug(2, "Connection %d: Remote Control connection from %s:%u to self at %s:%u.", - conn->connection_number, conn->client_ip_string, conn->client_rtsp_port, - conn->self_ip_string, conn->self_rtsp_port); + debug(1, "Connection %d: Remote Control connection from %s:%u (\"%s\") to self at %s:%u.", + conn->connection_number, conn->client_ip_string, conn->client_rtsp_port, clientNameString, + conn->self_ip_string, conn->self_rtsp_port); conn->airplay_stream_category = remote_control_stream; } else { debug(1, @@ -3354,6 +3369,8 @@ void handle_setup_2(rtsp_conn_info *conn, rtsp_message *req, rtsp_message *resp) msg_add_header(resp, "Content-Type", "application/x-apple-binary-plist"); } plist_free(messagePlist); + if (clientNameString != NULL) + free(clientNameString); debug_log_rtsp_message(2, " SETUP response", resp); } #endif @@ -3521,14 +3538,16 @@ void handle_set_parameter_parameter(rtsp_conn_info *conn, rtsp_message *req, debug(2, "Connection %d: request to set AirPlay Volume to: %f.", conn->connection_number, volume); // if we are playing, go ahead and change the volume - lock_player(); - config.airplay_volume = volume; - if (playing_conn == conn) - player_volume(volume, conn); - unlock_player(); #ifdef CONFIG_DBUS_INTERFACE if (dbus_service_is_running()) { - shairport_sync_set_volume(shairportSyncSkeleton, config.airplay_volume); + shairport_sync_set_volume(shairportSyncSkeleton, volume); + } else { +#endif + lock_player(); + if (playing_conn == conn) + player_volume(volume, conn); + unlock_player(); +#ifdef CONFIG_DBUS_INTERFACE } #endif } else if (strncmp(cp, "progress: ", strlen("progress: ")) == @@ -4407,7 +4426,9 @@ static void handle_announce(rtsp_conn_info *conn, rtsp_message *req, rtsp_messag #ifdef CONFIG_AIRPLAY_2 conn->airplay_type = ap_1; conn->timing_type = ts_ntp; - debug(1, "Connection %d. AirPlay 1 Audio Stream Detected.", conn->connection_number); + debug(1, "Connection %d: Classic AirPlay connection from %s:%u to self at %s:%u.", + conn->connection_number, conn->client_ip_string, conn->client_rtsp_port, + conn->self_ip_string, conn->self_rtsp_port); #endif conn->stream.type = ast_unknown; @@ -5460,7 +5481,7 @@ void *rtsp_listen_loop(__attribute((unused)) void *arg) { inet_ntop(conn->connection_ip_family, self_addr, conn->self_ip_string, sizeof(conn->self_ip_string)); - debug(1, "Connection %d: New connection from %s:%u to self at %s:%u.", + debug(2, "Connection %d: New connection from %s:%u to self at %s:%u.", conn->connection_number, conn->client_ip_string, conn->client_rtsp_port, conn->self_ip_string, conn->self_rtsp_port); conn->connection_start_time = get_absolute_time_in_ns(); From 2a70297945f267b90b7e97262fda9b00b0ea39b2 Mon Sep 17 00:00:00 2001 From: Mike Brady <4265913+mikebrady@users.noreply.github.com> Date: Wed, 5 Oct 2022 10:15:45 +0100 Subject: [PATCH 2/2] Fixes --- Makefile.am | 12 ++++++++++-- audio_alsa.c | 12 ++++++++---- 2 files changed, 18 insertions(+), 6 deletions(-) diff --git a/Makefile.am b/Makefile.am index b681ed3e..1dc654cc 100644 --- a/Makefile.am +++ b/Makefile.am @@ -267,9 +267,13 @@ if INSTALL_SYSTEMV INSTALL_SYSTEMV_TARGET = install-systemv-local +# watch out -- shairport-sync is created during the ./configure step and +# will be stored in a scripts folder in the _build_ folder +# which will be the source folder if you're not using a separate build folder + $(INSTALL_SYSTEMV_TARGET): scripts/shairport-sync $(INSTALL_USER_TARGET) install -d $(DESTDIR)$(sysconfdir)/init.d - [ -e $(DESTDIR)$(sysconfdir)/init.d/shairport-sync ] || install -m 0644 $(top_srcdir)/scripts/shairport-sync $(DESTDIR)$(sysconfdir)/init.d + [ -e $(DESTDIR)$(sysconfdir)/init.d/shairport-sync ] || install -m 0755 scripts/shairport-sync $(DESTDIR)$(sysconfdir)/init.d endif # INSTALL_SYSTEMV @@ -283,9 +287,13 @@ endif # USE_AVAHI INSTALL_SYSTEMD_TARGET = install-systemd-local +# watch out -- shairport-sync.service is created during the ./configure step and +# will be stored in a scripts folder in the _build_ folder +# which will be the source folder if you're not using a separate build folder + $(INSTALL_SYSTEMD_TARGET): scripts/$(SYSTEMD_SERVICE) $(INSTALL_USER_TARGET) install -d $(DESTDIR)$(systemdsystemunitdir) - [ -e $(DESTDIR)$(systemdsystemunitdir)/shairport-sync.service ] || install -m 0644 $(top_srcdir)/scripts/$(SYSTEMD_SERVICE) $(DESTDIR)$(systemdsystemunitdir)/shairport-sync.service + [ -e $(DESTDIR)$(systemdsystemunitdir)/shairport-sync.service ] || install -m 0644 scripts/$(SYSTEMD_SERVICE) $(DESTDIR)$(systemdsystemunitdir)/shairport-sync.service endif # INSTALL_SYSTEMD diff --git a/audio_alsa.c b/audio_alsa.c index fc53ee65..62db843f 100644 --- a/audio_alsa.c +++ b/audio_alsa.c @@ -1850,7 +1850,8 @@ static int do_close() { // debug(1,"alsa: do_close() -- closing the output device"); if ((derr = snd_pcm_drop(alsa_handle))) debug(1, "Error %d (\"%s\") dropping output device.", derr, snd_strerror(derr)); - usleep(5000); // this make the function pthread cancellable + usleep(10000); // wait for the hardware to do its trick. BTW, this make the function pthread + // cancellable if ((derr = snd_pcm_hw_free(alsa_handle))) debug(1, "Error %d (\"%s\") freeing the output device hardware.", derr, snd_strerror(derr)); debug(2, "alsa: do_close() -- closing alsa handle"); @@ -2061,9 +2062,12 @@ static void *alsa_buffer_monitor_thread_code(__attribute__((unused)) void *arg) int error_count = 0; int error_detected = 0; int okb = -1; - while (error_detected == - 0) { // if too many play errors occur early on, we will turn off the disable stanby mode + // if too many play errors occur early on, we will turn off the disable standby mode + while (error_detected == 0) { + int keep_dac_busy_has_just_gone_off = 0; if (okb != config.keep_dac_busy) { + if ((okb != 0) && (config.keep_dac_busy == 0)) + keep_dac_busy_has_just_gone_off = 1; debug(2, "keep_dac_busy is now \"%s\"", config.keep_dac_busy == 0 ? "no" : "yes"); okb = config.keep_dac_busy; } @@ -2081,7 +2085,7 @@ static void *alsa_buffer_monitor_thread_code(__attribute__((unused)) void *arg) if (do_open(1) == 0) // no automatic setup of rate and speed if necessary debug(2, "alsa: alsa_buffer_monitor_thread_code() -- output device opened; " "alsa_backend_state => abm_connected"); - } else if ((alsa_backend_state == abm_connected) && (config.keep_dac_busy == 0)) { + } else if ((alsa_backend_state != abm_disconnected) && (keep_dac_busy_has_just_gone_off != 0)) { stall_monitor_start_time = 0; // frame_index = 0; // measurement_data_is_valid = 0;