aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/conf.c1
-rw-r--r--src/conf.h1
-rw-r--r--src/main.c5
-rw-r--r--src/zeroconf.c128
4 files changed, 122 insertions, 13 deletions
diff --git a/src/conf.c b/src/conf.c
index 15d95a78b..307d85dfd 100644
--- a/src/conf.c
+++ b/src/conf.c
@@ -145,6 +145,7 @@ void initConf(void)
registerConfigParam(CONF_PORT, 0, 0);
registerConfigParam(CONF_LOG_LEVEL, 0, 0);
registerConfigParam(CONF_ZEROCONF_NAME, 0, 0);
+ registerConfigParam(CONF_ZEROCONF_ENABLED, 0, 0);
registerConfigParam(CONF_PASSWORD, 1, 0);
registerConfigParam(CONF_DEFAULT_PERMS, 0, 0);
registerConfigParam(CONF_AUDIO_OUTPUT, 1, 1);
diff --git a/src/conf.h b/src/conf.h
index 7059eaa90..f5ef07525 100644
--- a/src/conf.h
+++ b/src/conf.h
@@ -33,6 +33,7 @@
#define CONF_PORT "port"
#define CONF_LOG_LEVEL "log_level"
#define CONF_ZEROCONF_NAME "zeroconf_name"
+#define CONF_ZEROCONF_ENABLED "zeroconf_enabled"
#define CONF_PASSWORD "password"
#define CONF_DEFAULT_PERMS "default_permissions"
#define CONF_AUDIO_OUTPUT "audio_output"
diff --git a/src/main.c b/src/main.c
index 4c537eb1d..ddfe508b6 100644
--- a/src/main.c
+++ b/src/main.c
@@ -429,7 +429,6 @@ int main(int argc, char *argv[])
initAudioDriver();
initVolume();
initInterfaces();
- initZeroconf();
initReplayGainState();
initNormalization();
initInputStream();
@@ -438,10 +437,10 @@ int main(int argc, char *argv[])
setup_log_output(options.stdOutput);
-
-
initSigHandlers();
+ initZeroconf();
+
openVolumeDevice();
read_state_file();
diff --git a/src/zeroconf.c b/src/zeroconf.c
index 0b0163218..6ded363bf 100644
--- a/src/zeroconf.c
+++ b/src/zeroconf.c
@@ -19,6 +19,7 @@
#include <stdlib.h>
#include <assert.h>
#include <string.h>
+#include <arpa/inet.h>
#include "zeroconf.h"
#include "conf.h"
@@ -35,6 +36,17 @@
*/
#define SERVICE_NAME "Music Player"
+#ifdef HAVE_ZEROCONF
+static struct ioOps zeroConfIo = {
+};
+#endif
+
+#ifdef HAVE_BONJOUR
+#include <dns_sd.h>
+
+static DNSServiceRef dnsReference;
+#endif
+
/* Here is the implementation for Avahi (http://avahi.org) Zeroconf support */
#ifdef HAVE_AVAHI
@@ -55,10 +67,6 @@ static int avahiRunning;
static int avahiFdset( fd_set* rfds, fd_set* wfds, fd_set* efds );
static int avahiFdconsume( int fdCount, fd_set* rfds, fd_set* wfds, fd_set* efds );
-static struct ioOps avahiIo = {
- .fdset = avahiFdset,
- .consume = avahiFdconsume,
-};
/* Forward Declaration */
static void avahiRegisterService(AvahiClient *c);
@@ -453,36 +461,127 @@ static void init_avahi(const char *serviceName)
goto fail;
}
- avahiIo.fdset = avahiFdset;
- avahiIo.consume = avahiFdconsume;
- registerIO( &avahiIo );
+ zeroConfIo.fdset = avahiFdset;
+ zeroConfIo.consume = avahiFdconsume;
+ registerIO( &zeroConfIo );
return;
fail:
finishZeroconf();
}
-#else /* !HAVE_AVAHI */
-static void init_avahi(const char *serviceName) { }
#endif /* HAVE_AVAHI */
+#ifdef HAVE_BONJOUR
+static int dnsRegisterFdset(fd_set* rfds, fd_set* wfds, fd_set* efds)
+{
+ int fd;
+
+ if (dnsReference == NULL)
+ return -1;
+
+ fd = DNSServiceRefSockFD(dnsReference);
+ if (fd == -1)
+ return -1;
+
+ FD_SET(fd, rfds);
+
+ return fd;
+}
+
+static int dnsRegisterFdconsume(int fdCount, fd_set* rfds, fd_set* wfds,
+ fd_set* efds)
+{
+ int fd;
+
+ if (dnsReference == NULL)
+ return -1;
+
+ fd = DNSServiceRefSockFD(dnsReference);
+ if (fd == -1)
+ return -1;
+
+ if (FD_ISSET(fd, rfds)) {
+ FD_CLR(fd, rfds);
+
+ DNSServiceProcessResult(dnsReference);
+
+ return fdCount - 1;
+ }
+
+ return fdCount;
+}
+
+static void dnsRegisterCallback (DNSServiceRef sdRef, DNSServiceFlags flags,
+ DNSServiceErrorType errorCode, const char *name,
+ const char *regtype, const char *domain, void *context)
+{
+ if (errorCode != kDNSServiceErr_NoError) {
+ ERROR("Failed to register zeroconf service.\n");
+
+ DNSServiceRefDeallocate(dnsReference);
+ dnsReference = NULL;
+ deregisterIO( &zeroConfIo );
+ } else {
+ DEBUG("Registered zeroconf service with name '%s'\n", name);
+ }
+}
+
+static void init_zeroconf_osx(const char *serviceName)
+{
+ DNSServiceErrorType error = DNSServiceRegister(&dnsReference,
+ 0, 0, serviceName, SERVICE_TYPE, NULL, NULL, htons(getBoundPort()), 0,
+ NULL, dnsRegisterCallback, NULL);
+
+ if (error != kDNSServiceErr_NoError) {
+ ERROR("Failed to register zeroconf service.\n");
+
+ if (dnsReference) {
+ DNSServiceRefDeallocate(dnsReference);
+ dnsReference = NULL;
+ }
+ return;
+ }
+
+ zeroConfIo.fdset = dnsRegisterFdset;
+ zeroConfIo.consume = dnsRegisterFdconsume;
+ registerIO( &zeroConfIo );
+}
+#endif
+
void initZeroconf(void)
{
const char* serviceName = SERVICE_NAME;
ConfigParam *param;
+ int enabled = getBoolConfigParam(CONF_ZEROCONF_ENABLED);
+
+ if (enabled != -1 && enabled != 1)
+ return;
param = getConfigParam(CONF_ZEROCONF_NAME);
if (param && strlen(param->value) > 0)
serviceName = param->value;
+
+#ifdef HAVE_AVAHI
init_avahi(serviceName);
+#endif
+
+#ifdef HAVE_BONJOUR
+ init_zeroconf_osx(serviceName);
+#endif
}
void finishZeroconf(void)
{
+ int enabled = getBoolConfigParam(CONF_ZEROCONF_ENABLED);
+
+ if (enabled != -1 && enabled != 1)
+ return;
+
#ifdef HAVE_AVAHI
DEBUG( "Avahi: Shutting down interface\n" );
- deregisterIO( &avahiIo );
+ deregisterIO( &zeroConfIo );
if( avahiGroup ) {
avahi_entry_group_free( avahiGroup );
@@ -497,4 +596,13 @@ void finishZeroconf(void)
avahi_free( avahiName );
avahiName = NULL;
#endif /* HAVE_AVAHI */
+
+#ifdef HAVE_BONJOUR
+ deregisterIO( &zeroConfIo );
+ if (dnsReference != NULL) {
+ DNSServiceRefDeallocate(dnsReference);
+ dnsReference = NULL;
+ DEBUG("Deregistered Zeroconf service.\n");
+ }
+#endif
}