--- /dev/null
+#
+# Copyright (C) 2013 OpenWrt.org
+#
+# This is free software, licensed under the GNU General Public License v2.
+# See /LICENSE for more information.
+#
+
+include $(TOPDIR)/rules.mk
+
+PKG_NAME:=shairport
+PKG_VERSION:=2012-10-20
+PKG_RELEASE:=$(PKG_SOURCE_VERSION)
+
+PKG_SOURCE_PROTO:=git
+PKG_SOURCE_URL:=git://github.com/albertz/shairport.git
+PKG_SOURCE_SUBDIR:=$(PKG_NAME)-$(PKG_VERSION)
+PKG_SOURCE_VERSION:=4746bb11395d171ee800f074f489c42020a84932
+PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION)-$(PKG_SOURCE_VERSION).tar.gz
+
+include $(INCLUDE_DIR)/package.mk
+
+define Package/shairport
+ SECTION:=multimedia
+ CATEGORY:=Multimedia
+ DEPENDS:=+libpthread +avahi-utils +libopenssl +libao
+ TITLE:=ShairPort AirPort Express emulator
+endef
+
+define Package/shairport/description
+ This program emulates an AirPort Express for the purpose of streaming
+ music from iTunes and compatible iPods. It implements a server for the
+ Apple RAOP protocol.
+ ShairPort does not support AirPlay v2 (video and photo streaming).
+
+ It supports multiple simultaneous streams, if your audio output chain
+ (as detected by libao) does so.
+endef
+
+TARGET_CFLAGS += $(FPIC)
+
+LIBS:=-lao -lm -lcrypto -lpthread
+
+MAKE_FLAGS += \
+ CFLAGS="$(TARGET_CFLAGS) $(TARGET_CPPFLAGS)" \
+ LDFLAGS="$(TARGET_LDFLAGS) $(LIBS)"
+
+define Package/shairport/install
+ $(INSTALL_DIR) $(1)/usr/sbin
+ $(INSTALL_BIN) $(PKG_BUILD_DIR)/shairport $(1)/usr/sbin/
+ $(INSTALL_DIR) $(1)/etc/init.d/
+ $(INSTALL_BIN) files/shairport.init $(1)/etc/init.d/shairport
+ $(INSTALL_DIR) $(1)/etc/config
+ $(INSTALL_DATA) files/shairport.config $(1)/etc/config/shairport
+endef
+
+$(eval $(call BuildPackage,shairport))
--- /dev/null
+diff --git a/socketlib.c b/socketlib.c
+index 9efdf22..eb44bcf 100644
+--- a/socketlib.c
++++ b/socketlib.c
+@@ -39,9 +39,11 @@
+ #include <openssl/bio.h>
+ #include <openssl/buffer.h>
+
+-int common_setup(struct addrinfo *pAddrInfo)
+-{
++int common_setup(struct addrinfo **ppAddrInfo, int pPort)
++{
+ int tSock;
++ struct addrinfo *pAddrInfo = *ppAddrInfo;
++
+ //printAddrs(pAddrInfo);
+ tSock = socket(pAddrInfo->ai_family, pAddrInfo->ai_socktype, 0);
+ #ifdef AF_INET6
+@@ -49,7 +51,17 @@ int common_setup(struct addrinfo *pAddrInfo)
+ {
+ //Fallback to ipv4
+ perror("Failed to create ipv6 socket. Trying ipv4");
+- pAddrInfo->ai_family = AF_INET;
++ (*ppAddrInfo)->ai_family = AF_INET;
++ if (pPort != -1)
++ {
++ char tService[SERVLEN];
++ sprintf(tService, "%d", pPort); // copies port to string
++ int tFamily = AF_INET;
++ if(getAddr(NULL, tService, tFamily, SOCK_STREAM, ppAddrInfo))
++ {
++ return ERROR; // getAddr prints out error message
++ }
++ }
+ tSock = socket(pAddrInfo->ai_family, pAddrInfo->ai_socktype, 0);
+ }
+ #endif
+@@ -63,7 +75,7 @@ int setup_client(struct addrinfo *server_host)
+
+ while(tIdx++ < RETRY_COUNT)
+ {
+- tSockDesc = common_setup(server_host);
++ tSockDesc = common_setup(&server_host, -1);
+ if (tSockDesc < 0 && tIdx >= RETRY_COUNT)
+ {
+ perror("Error: Could not create socket");
+@@ -107,9 +119,23 @@ int getAddr(char *pHostname, char *pService, int pFamily, int pSockType, struct
+ return tError;
+ }
+
+-int setup_server(struct addrinfo *server_addr)
++int setup_server(struct addrinfo *server_addr, int pPort)
+ {
+- int tSock = common_setup(server_addr);
++ char tService[SERVLEN];
++ sprintf(tService, "%d", pPort); // copies port to string
++ int tFamily = AF_INET;
++ #ifdef AF_INET6
++ //printf("Listening on IPv6 Socket\n");
++ tFamily = AF_INET6;
++ #else
++ //printf("Listening on IPv4 Socket");
++ #endif
++ if(getAddr(NULL, tService, tFamily, SOCK_STREAM, &server_addr))
++ {
++ return ERROR; // getAddr prints out error message
++ }
++
++ int tSock = common_setup(&server_addr, pPort);
+ if (tSock < 0)
+ {
+ perror("Error: Could not create server socket");
+@@ -154,21 +180,7 @@ int acceptClient(int pSock, struct addrinfo *server_addr)
+
+ int setupListenServer(struct addrinfo **pAddrInfo, int pPort)
+ {
+- char tService[SERVLEN];
+- sprintf(tService, "%d", pPort); // copies port to string
+- int tFamily = AF_INET;
+- #ifdef AF_INET6
+- //printf("Listening on IPv6 Socket\n");
+- tFamily = AF_INET6;
+- #else
+- //printf("Listening on IPv4 Socket");
+- #endif
+- if(getAddr(NULL, tService, tFamily, SOCK_STREAM, pAddrInfo))
+- {
+- return ERROR; // getAddr prints out error message
+- }
+-
+- int tSocketDescriptor = setup_server(*pAddrInfo);
++ int tSocketDescriptor = setup_server(*pAddrInfo, pPort);
+ char tAddr[INET6_ADDRSTRLEN];
+ socklen_t tSize = INET6_ADDRSTRLEN;
+ inet_ntop((*pAddrInfo)->ai_family, (*pAddrInfo)->ai_addr, tAddr, tSize);
+diff --git a/socketlib.h b/socketlib.h
+index 6d501f3..5cb1bf0 100644
+--- a/socketlib.h
++++ b/socketlib.h
+@@ -24,7 +24,7 @@
+ #define DEFAULT_UNIX "/unix"
+
+ int setup_client(struct addrinfo *server_info);
+-int setup_server(struct addrinfo *server_address);
++int setup_server(struct addrinfo *server_address, int pPort);
+ int setupListenServer(struct addrinfo **pAddrInfo, int pPort);
+ int acceptClient(int pSock, struct addrinfo *server_addr);
+ void delay(long pMillisecs, struct timeval *pRes);