/*
 * libusbmuxd.c
 *
 * Copyright (C) 2009-2019 Nikias Bassen <nikias@gmx.li>
 * Copyright (C) 2009-2014 Martin Szulecki <m.szulecki@libimobiledevice.org>
 * Copyright (C) 2009 Paul Sladen <libiphone@paul.sladen.org>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 */

#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <stdint.h>
#include <stdlib.h>
#include <errno.h>
#include <stdio.h>
#include <string.h>

#ifdef LIBUSBMUXD_STATIC
  #define USBMUXD_API
#elif defined(_WIN32)
  #define USBMUXD_API __declspec( dllexport )
#else
  #if __GNUC__ >= 4
    #define USBMUXD_API __attribute__((visibility("default")))
  #else
    #define USBMUXD_API
  #endif
#endif

#ifndef EPROTO
#define EPROTO 134
#endif
#ifndef EBADMSG
#define EBADMSG 104
#endif
#ifndef ECONNREFUSED
#define ECONNREFUSED 107
#endif

#ifdef _WIN32
#include <winsock2.h>
#include <windows.h>
#define sleep(x) Sleep(x*1000)
#else
#include <unistd.h>
#include <signal.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#if defined(HAVE_PROGRAM_INVOCATION_SHORT_NAME) && !defined(HAVE_PROGRAM_INVOCATION_SHORT_NAME_ERRNO_H)
extern char *program_invocation_short_name;
#endif
#ifdef __APPLE__
extern int _NSGetExecutablePath(char* buf, uint32_t* bufsize);
#include <sys/stat.h>
#endif
#endif

#ifdef HAVE_INOTIFY
#include <sys/inotify.h>
#include <sys/select.h>
#include <pthread.h>
#define EVENT_SIZE  (sizeof (struct inotify_event))
#define EVENT_BUF_LEN (1024 * (EVENT_SIZE + 16))
#define USBMUXD_DIRNAME "/var/run"
#define USBMUXD_SOCKET_NAME "usbmuxd"
static int use_inotify = 1;
#endif /* HAVE_INOTIFY */

#ifndef HAVE_STPNCPY
static char* stpncpy(char *dst, const char *src, size_t len)
{
	size_t n = strlen(src);
	if (n > len)
		n = len;
	return strncpy(dst, src, len) + n;
}
#endif

#ifdef _MSC_VER
#define strcasecmp _stricmp
#endif

#include <plist/plist.h>
#define PLIST_LIBUSBMUX_VERSION 3

static char *bundle_id = NULL;
static char *prog_name = NULL;

// usbmuxd public interface
#include "usbmuxd.h"
// usbmuxd protocol
#include "usbmuxd-proto.h"
// socket utility functions
#include <libimobiledevice-glue/socket.h>
// misc utility functions
#include <libimobiledevice-glue/collection.h>
// threads
#include <libimobiledevice-glue/thread.h>

static int libusbmuxd_debug = 0;
#ifndef PACKAGE
#define PACKAGE "libusbmuxd"
#endif
#ifndef PACKAGE_NAME
#define PACKAGE_NAME PACKAGE
#endif
#define LIBUSBMUXD_DEBUG(level, format, ...) if (level <= libusbmuxd_debug) fprintf(stderr, ("[" PACKAGE "] " format), __VA_ARGS__); fflush(stderr);
#define LIBUSBMUXD_ERROR(format, ...) LIBUSBMUXD_DEBUG(0, format, __VA_ARGS__)

static struct collection devices;
static THREAD_T devmon = THREAD_T_NULL;
static int listenfd = -1;
static int running = 0;
static int cancelling = 0;

static volatile int use_tag = 0;
static volatile int proto_version = 1;
static volatile int try_list_devices = 1;

struct usbmuxd_subscription_context {
	usbmuxd_event_cb_t callback;
	void *user_data;
};

static struct usbmuxd_subscription_context *event_ctx = NULL;

static struct collection listeners;
thread_once_t listener_init_once = THREAD_ONCE_INIT;
mutex_t listener_mutex;

/**
 * Finds a device info record by its handle.
 * if the record is not found, NULL is returned.
 */
static usbmuxd_device_info_t *devices_find(uint32_t handle)
{
	FOREACH(usbmuxd_device_info_t *dev, &devices) {
		if (dev && dev->handle == handle) {
			return dev;
		}
	} ENDFOREACH
	return NULL;
}

/**
 * Creates a socket connection to usbmuxd.
 * For Mac/Linux it is a unix domain socket,
 * for Windows it is a tcp socket.
 */
static int connect_usbmuxd_socket()
{
	int res = -1;
	char *usbmuxd_socket_addr = getenv("USBMUXD_SOCKET_ADDRESS");
	if (usbmuxd_socket_addr) {
		if (strncmp(usbmuxd_socket_addr, "UNIX:", 5) == 0) {
#if defined(_WIN32) || defined(__CYGWIN__)
			/* not supported, ignore */
#else
			if (usbmuxd_socket_addr[5] != '\0') {
				res = socket_connect_unix(usbmuxd_socket_addr+5);
				if (res < 0) {
					res = -errno;
				}
				return res;
			}
#endif
		} else {
			uint16_t port = 0;
			char *p = strrchr(usbmuxd_socket_addr, ':');
			if (p) {
				char *endp = NULL;
				long l_port = strtol(p+1, &endp, 10);
				if (endp && *endp == '\0') {
					if (l_port > 0 && l_port < 65536) {
						port = (uint16_t)l_port;
					}
				}
			}
			if (p && port > 0) {
				char *connect_addr = NULL;
				if (usbmuxd_socket_addr[0] == '[') {
					connect_addr = strdup(usbmuxd_socket_addr+1);
					connect_addr[p - usbmuxd_socket_addr - 1] = '\0';
					p = strrchr(connect_addr, ']');
					if (p) {
						*p = '\0';
					}
				} else {
					connect_addr = strdup(usbmuxd_socket_addr);
					connect_addr[p - usbmuxd_socket_addr] = '\0';
				}
				if (connect_addr && *connect_addr != '\0') {
					res = socket_connect(connect_addr, port);
#ifdef HAVE_INOTIFY
					use_inotify = 0;
#endif
					free(connect_addr);
					if (res < 0) {
						res = -errno;
					}
					return res;
				}
				free(connect_addr);
			}
		}
	}
#if defined(_WIN32) || defined(__CYGWIN__)
	res = socket_connect("127.0.0.1", USBMUXD_SOCKET_PORT);
#else
	res = socket_connect_unix(USBMUXD_SOCKET_FILE);
#endif
	if (res < 0) {
		res = -errno;
	}
	return res;
}

static void sanitize_udid(usbmuxd_device_info_t *devinfo)
{
	if (!devinfo)
		return;
	if (strlen(devinfo->udid) == 24) {
		memmove(&devinfo->udid[9], &devinfo->udid[8], 17);
		devinfo->udid[8] = '-';
	}
	if (strcasecmp(devinfo->udid, "ffffffffffffffffffffffffffffffffffffffff") == 0) {
		sprintf(devinfo->udid + 32, "%08x", devinfo->handle);
	}
}

static usbmuxd_device_info_t *device_info_from_plist(plist_t props)
{
	usbmuxd_device_info_t* devinfo = NULL;
	plist_t n = NULL;
	uint64_t val = 0;
	char *strval = NULL;

	devinfo = (usbmuxd_device_info_t*)malloc(sizeof(usbmuxd_device_info_t));
	if (!devinfo)
		return NULL;
	memset(devinfo, 0, sizeof(usbmuxd_device_info_t));

	n = plist_dict_get_item(props, "DeviceID");
	if (n && plist_get_node_type(n) == PLIST_UINT) {
		plist_get_uint_val(n, &val);
		devinfo->handle = (uint32_t)val;
	}

	n = plist_dict_get_item(props, "ProductID");
	if (n && plist_get_node_type(n) == PLIST_UINT) {
		plist_get_uint_val(n, &val);
		devinfo->product_id = (uint32_t)val;
	}

	n = plist_dict_get_item(props, "SerialNumber");
	if (n && plist_get_node_type(n) == PLIST_STRING) {
		plist_get_string_val(n, &strval);
		if (strval) {
			char *t = stpncpy(devinfo->udid, strval, sizeof(devinfo->udid)-1);
			*t = '\0';
			sanitize_udid(devinfo);
			free(strval);
		}
	}

	n = plist_dict_get_item(props, "ConnectionType");
	if (n && plist_get_node_type(n) == PLIST_STRING) {
		plist_get_string_val(n, &strval);
		if (strval) {
			if (strcmp(strval, "USB") == 0) {
				devinfo->conn_type = CONNECTION_TYPE_USB;
			} else if (strcmp(strval, "Network") == 0) {
				devinfo->conn_type = CONNECTION_TYPE_NETWORK;
				n = plist_dict_get_item(props, "NetworkAddress");
				if (n && plist_get_node_type(n) == PLIST_DATA) {
					uint64_t addr_len = 0;
					const char *netaddr = plist_get_data_ptr(n, &addr_len);
					if (netaddr && addr_len > 0 && addr_len < sizeof(devinfo->conn_data)) {
						memcpy(devinfo->conn_data, netaddr, addr_len);
					}
				}
			} else {
				LIBUSBMUXD_ERROR("%s: Unexpected ConnectionType '%s'\n", __func__, strval);
			}
			free(strval);
		}
	}

	if (!devinfo->udid[0]) {
		LIBUSBMUXD_ERROR("%s: Failed to get SerialNumber (UDID)!\n", __func__);
		free(devinfo);
		return NULL;
	}
	if (!devinfo->conn_type) {
		LIBUSBMUXD_ERROR("%s: Failed to get ConnectionType!\n", __func__);
		free(devinfo);
		devinfo = NULL;
	} else if (devinfo->conn_type == CONNECTION_TYPE_NETWORK && !devinfo->conn_data[0]) {
		LIBUSBMUXD_ERROR("%s: Failed to get EscapedFullServiceName!\n", __func__);
		free(devinfo);
		devinfo = NULL;
	}

	return devinfo;
}

static usbmuxd_device_info_t *device_info_from_device_record(struct usbmuxd_device_record *dev)
{
	if (!dev) {
		return NULL;
	}
	usbmuxd_device_info_t *devinfo = (usbmuxd_device_info_t*)malloc(sizeof(usbmuxd_device_info_t));
	if (!devinfo) {
		LIBUSBMUXD_ERROR("%s: Out of memory while allocating device info object\n", __func__);
		return NULL;
	}

	devinfo->handle = dev->device_id;
	devinfo->product_id = dev->product_id;
	char *t = stpncpy(devinfo->udid, dev->serial_number, sizeof(devinfo->udid)-2);
	*t = '\0';
	sanitize_udid(devinfo);

	return devinfo;
}

static int receive_packet(int sfd, struct usbmuxd_header *header, void **payload, int timeout)
{
	int recv_len;
	struct usbmuxd_header hdr;
	char *payload_loc = NULL;

	header->length = 0;
	header->version = 0;
	header->message = 0;
	header->tag = 0;

	recv_len = socket_receive_timeout(sfd, &hdr, sizeof(hdr), 0, timeout);
	if (recv_len < 0) {
		if (!cancelling) {
			LIBUSBMUXD_DEBUG(1, "%s: Error receiving packet: %s\n", __func__, strerror(-recv_len));
		}
		return recv_len;
	}

	if ((size_t)recv_len < sizeof(hdr)) {
		LIBUSBMUXD_DEBUG(1, "%s: Received packet is too small, got %d bytes!\n", __func__, recv_len);
		return recv_len;
	}

	uint32_t payload_size = hdr.length - sizeof(hdr);
	if (payload_size > 0) {
		payload_loc = (char*)malloc(payload_size);
		uint32_t rsize = 0;
		do {
			int res = socket_receive_timeout(sfd, payload_loc + rsize, payload_size - rsize, 0, 5000);
			if (res < 0) {
				break;
			}
			rsize += res;
		} while (rsize < payload_size);
		if (rsize != payload_size) {
			LIBUSBMUXD_DEBUG(1, "%s: Error receiving payload of size %d (bytes received: %d)\n", __func__, payload_size, rsize);
			free(payload_loc);
			return -EBADMSG;
		}
	}

	if (hdr.message == MESSAGE_PLIST) {
		char *message = NULL;
		plist_t plist = NULL;
		plist_from_xml(payload_loc, payload_size, &plist);
		free(payload_loc);

		if (!plist) {
			LIBUSBMUXD_DEBUG(1, "%s: Error getting plist from payload!\n", __func__);
			return -EBADMSG;
		}

		plist_t node = plist_dict_get_item(plist, "MessageType");
		if (!node || plist_get_node_type(node) != PLIST_STRING) {
			*payload = plist;
			hdr.length = sizeof(hdr);
			memcpy(header, &hdr, sizeof(hdr));
			return hdr.length;
		}

		plist_get_string_val(node, &message);
		if (message) {
			uint64_t val = 0;
			if (strcmp(message, "Result") == 0) {
				/* result message */
				uint32_t dwval = 0;
				plist_t n = plist_dict_get_item(plist, "Number");
				plist_get_uint_val(n, &val);
				*payload = malloc(sizeof(uint32_t));
				dwval = val;
				memcpy(*payload, &dwval, sizeof(dwval));
				hdr.length = sizeof(hdr) + sizeof(dwval);
				hdr.message = MESSAGE_RESULT;
			} else if (strcmp(message, "Attached") == 0) {
				/* device add message */
				usbmuxd_device_info_t *devinfo = NULL;
				plist_t props = plist_dict_get_item(plist, "Properties");
				if (!props) {
					LIBUSBMUXD_DEBUG(1, "%s: Could not get properties for message '%s' from plist!\n", __func__, message);
					free(message);
					plist_free(plist);
					return -EBADMSG;
				}

				devinfo = device_info_from_plist(props);
				if (!devinfo) {
					LIBUSBMUXD_DEBUG(1, "%s: Could not create device info object from properties!\n", __func__);
					free(message);
					plist_free(plist);
					return -EBADMSG;
				}
				*payload = (void*)devinfo;
				hdr.length = sizeof(hdr) + sizeof(usbmuxd_device_info_t);
				hdr.message = MESSAGE_DEVICE_ADD;
			} else if (strcmp(message, "Detached") == 0) {
				/* device remove message */
				uint32_t dwval = 0;
				plist_t n = plist_dict_get_item(plist, "DeviceID");
				if (n) {
					plist_get_uint_val(n, &val);
					*payload = malloc(sizeof(uint32_t));
					dwval = val;
					memcpy(*payload, &dwval, sizeof(dwval));
					hdr.length = sizeof(hdr) + sizeof(dwval);
					hdr.message = MESSAGE_DEVICE_REMOVE;
				}
			} else if (strcmp(message, "Paired") == 0) {
				/* device pair message */
				uint32_t dwval = 0;
				plist_t n = plist_dict_get_item(plist, "DeviceID");
				if (n) {
					plist_get_uint_val(n, &val);
					*payload = malloc(sizeof(uint32_t));
					dwval = val;
					memcpy(*payload, &dwval, sizeof(dwval));
					hdr.length = sizeof(hdr) + sizeof(dwval);
					hdr.message = MESSAGE_DEVICE_PAIRED;
				}
			} else {
				char *xml = NULL;
				uint32_t len = 0;
				plist_to_xml(plist, &xml, &len);
				LIBUSBMUXD_DEBUG(1, "%s: Unexpected message '%s' in plist:\n%s\n", __func__, message, xml);
				free(xml);
				free(message);
				plist_free(plist);
				return -EBADMSG;
			}
			free(message);
		}
		plist_free(plist);
	} else if (hdr.message == MESSAGE_DEVICE_ADD) {
		usbmuxd_device_info_t *devinfo = device_info_from_device_record((struct usbmuxd_device_record*)payload_loc);
		free(payload_loc);
		*payload = devinfo;
	} else {
		*payload = payload_loc;
	}

	memcpy(header, &hdr, sizeof(hdr));

	return hdr.length;
}

/**
 * Retrieves the result code to a previously sent request.
 */
static int usbmuxd_get_result(int sfd, uint32_t tag, uint32_t *result, void **result_plist)
{
	struct usbmuxd_header hdr;
	int recv_len;
	uint32_t *res = NULL;

	if (!result) {
		return -EINVAL;
	}
	*result = -1;
	if (result_plist) {
		*result_plist = NULL;
	}

	recv_len = receive_packet(sfd, &hdr, (void**)&res, 5000);
	if (recv_len < 0 || (size_t)recv_len < sizeof(hdr)) {
		free(res);
		return (recv_len < 0 ? recv_len : -EPROTO);
	}

	if (hdr.message == MESSAGE_RESULT) {
		int ret = 0;
		if (hdr.tag != tag) {
			LIBUSBMUXD_DEBUG(1, "%s: WARNING: tag mismatch (%d != %d). Proceeding anyway.\n", __func__, hdr.tag, tag);
		}
		if (res) {
			memcpy(result, res, sizeof(uint32_t));
			ret = 1;
		}
		free(res);
		return ret;
	}

	if (hdr.message == MESSAGE_PLIST) {
		if (!result_plist) {
			LIBUSBMUXD_DEBUG(1, "%s: MESSAGE_PLIST result but result_plist pointer is NULL!\n", __func__);
			return -1;
		}
		*result_plist = (plist_t)res;
		*result = RESULT_OK;
		return 1;
	}

	LIBUSBMUXD_DEBUG(1, "%s: Unexpected message of type %d received!\n", __func__, hdr.message);
	free(res);
	return -EPROTO;
}

static int send_packet(int sfd, uint32_t message, uint32_t tag, void *payload, uint32_t payload_size)
{
	struct usbmuxd_header header;

	header.length = sizeof(struct usbmuxd_header);
	header.version = proto_version;
	header.message = message;
	header.tag = tag;
	if (payload && (payload_size > 0)) {
		header.length += payload_size;
	}
	int sent = socket_send(sfd, &header, sizeof(header));
	if (sent != sizeof(header)) {
		LIBUSBMUXD_DEBUG(1, "%s: ERROR: could not send packet header\n", __func__);
		return -1;
	}
	if (payload && (payload_size > 0)) {
		uint32_t ssize = 0;
		do {
			int res = socket_send(sfd, (char*)payload + ssize, payload_size - ssize);
			if (res < 0) {
				break;
			}
			ssize += res;
		} while (ssize < payload_size);
		sent += ssize;
	}
	if (sent != (int)header.length) {
		LIBUSBMUXD_DEBUG(1, "%s: ERROR: could not send whole packet (sent %d of %d)\n", __func__, sent, header.length);
		socket_close(sfd);
		return -1;
	}
	return sent;
}

static int send_plist_packet(int sfd, uint32_t tag, plist_t message)
{
	int res;
	char *payload = NULL;
	uint32_t payload_size = 0;

	plist_to_xml(message, &payload, &payload_size);
	res = send_packet(sfd, MESSAGE_PLIST, tag, payload, payload_size);
	free(payload);

	return res;
}

static void get_bundle_id()
{
#if defined (__APPLE__)
	char CONTENTS_INFO_PLIST[] = "Contents/Info.plist";
	char* execpath = malloc(1024);
	uint32_t size = 1024;
	if (_NSGetExecutablePath(execpath, &size) != 0) {
		free(execpath);
		return;
	}
	// strip off executable name
	char *p = execpath + strlen(execpath) - 1;
	while (p > execpath && *p != '/') p--;
	if (*p == '/') *p = '\0';
	// now walk back trying to find "/Contents/MacOS", and strip it off
	int macos_found = 0;
	while (p > execpath) {
		p--;
		if (*p != '/') continue;
		if (strcmp(p, "/.") == 0) {
			*p = '\0';
		} else if (!macos_found && strcmp(p, "/MacOS") == 0) {
			*p = '\0';
			macos_found++;
		} else if (macos_found && strcmp(p, "/Contents") == 0) {
			*p = '\0';
			break;
		} else {
			break;
		}
	}
	// now just append "/Contents/Info.plist"
	size_t len = strlen(execpath) + sizeof(CONTENTS_INFO_PLIST) + 1;
	char *infopl = malloc(len);
	snprintf(infopl, len, "%s/%s", execpath, CONTENTS_INFO_PLIST);
	free(execpath);
	struct stat fst;
	fst.st_size = 0;
	if (stat(infopl, &fst) != 0) {
		free(infopl);
		return;
	}
	size_t fsize = fst.st_size;
	if (fsize < 8) {
		free(infopl);
		return;
	}
	FILE *f = fopen(infopl, "r");
	free(infopl);
	if (!f)
		return;
	char *buf = malloc(fsize);
	if (!buf)
		return;
	if (fread(buf, 1, fsize, f) == fsize) {
		plist_t pl = NULL;
		if (memcmp(buf, "bplist00", 8) == 0) {
			plist_from_bin(buf, fst.st_size, &pl);
		} else {
			plist_from_xml(buf, fst.st_size, &pl);
		}
		if (pl) {
			plist_t bid = plist_dict_get_item(pl, "CFBundleIdentifier");
			if (plist_get_node_type(bid) == PLIST_STRING) {
				plist_get_string_val(bid, &bundle_id);
			}
			plist_free(pl);
		}
	}
	free(buf);
	fclose(f);
#endif
}

static void get_prog_name()
{
#if defined(__APPLE__) || defined(__FreeBSD__)
	const char *pname = getprogname();
	if (pname) {
		prog_name = strdup(pname);
	}
#elif defined (_WIN32)
	TCHAR *_pname = malloc((MAX_PATH+1) * sizeof(TCHAR));
	if (GetModuleFileName(NULL, _pname, MAX_PATH+1) > 0) {
		char* pname = NULL;
	#if defined(UNICODE) || defined(_UNICODE)
		char* __pname = NULL;
		int l = WideCharToMultiByte(CP_UTF8, 0, _pname, -1, NULL, 0, NULL, NULL);
		if (l > 0) {
			__pname = malloc(l);
			if (WideCharToMultiByte(CP_UTF8, 0, _pname, -1, __pname, l, NULL, NULL) > 0) {
				pname = __pname;
			}
		}
	#else
		pname = _pname;
	#endif
		if (pname) {
			char *p = pname+strlen(pname)-1;
			while (p > pname && *p != '\\' && *p != '/') p--;
			if (*p == '\\' || *p == '/') p++;
			prog_name = strdup(p);
		}
	#if defined(UNICODE) || defined(_UNICODE)
		free(__pname);
	#endif
	}
	free(_pname);
#elif defined (HAVE_PROGRAM_INVOCATION_SHORT_NAME)
	char *pname = program_invocation_short_name;
	if (pname) {
		prog_name = strdup(pname);
	}
#elif defined (__linux__)
	FILE *f = fopen("/proc/self/stat", "r");
	if (!f) {
		return;
	}
	char *tmpbuf = malloc(512);
	size_t r = fread(tmpbuf, 1, 512, f);
	if (r > 0) {
		char *p = tmpbuf;
		while (((size_t)(p-tmpbuf) < r) && (*p != '(') && (*p != '\0')) p++;
		if (*p == '(') {
			p++;
			char *pname = p;
			while (((size_t)(p-tmpbuf) < r) && (*p != ')') && (*p != '\0')) p++;
			if (*p == ')') {
				*p = '\0';
				prog_name = strdup(pname);
			}
		}
	}
	free(tmpbuf);
	fclose(f);
#else
	#warning FIXME: no method to determine program name
#endif
}

static plist_t create_plist_message(const char* message_type)
{
	char client_version[128];
	snprintf(client_version, 128, PACKAGE_NAME " %s", libusbmuxd_version());
	if (!bundle_id) {
		get_bundle_id();
	}
	if (!prog_name) {
		get_prog_name();
	}
	plist_t plist = plist_new_dict();
	if (bundle_id) {
		plist_dict_set_item(plist, "BundleID", plist_new_string(bundle_id));
	}
	plist_dict_set_item(plist, "ClientVersionString", plist_new_string(client_version));
	plist_dict_set_item(plist, "MessageType", plist_new_string(message_type));
	if (prog_name) {
		plist_dict_set_item(plist, "ProgName", plist_new_string(prog_name));
	}
	plist_dict_set_item(plist, "kLibUSBMuxVersion", plist_new_uint(PLIST_LIBUSBMUX_VERSION));
	return plist;
}

static int send_listen_packet(int sfd, uint32_t tag)
{
	int res = 0;
	if (proto_version == 1) {
		/* construct message plist */
		plist_t plist = create_plist_message("Listen");

		res = send_plist_packet(sfd, tag, plist);
		plist_free(plist);
	} else {
		/* binary packet */
		res = send_packet(sfd, MESSAGE_LISTEN, tag, NULL, 0);
	}
	return res;
}

static int send_connect_packet(int sfd, uint32_t tag, uint32_t device_id, uint16_t port)
{
	int res = 0;
	if (proto_version == 1) {
		/* construct message plist */
		plist_t plist = create_plist_message("Connect");
		plist_dict_set_item(plist, "DeviceID", plist_new_uint(device_id));
		plist_dict_set_item(plist, "PortNumber", plist_new_uint(htons(port)));

		res = send_plist_packet(sfd, tag, plist);
		plist_free(plist);
	} else {
		/* binary packet */
		struct {
			uint32_t device_id;
			uint16_t port;
			uint16_t reserved;
		} conninfo;

		conninfo.device_id = device_id;
		conninfo.port = htons(port);
		conninfo.reserved = 0;

		res = send_packet(sfd, MESSAGE_CONNECT, tag, &conninfo, sizeof(conninfo));
	}
	return res;
}

static int send_list_devices_packet(int sfd, uint32_t tag)
{
	int res = -1;

	/* construct message plist */
	plist_t plist = create_plist_message("ListDevices");

	res = send_plist_packet(sfd, tag, plist);
	plist_free(plist);

	return res;
}

static int send_read_buid_packet(int sfd, uint32_t tag)
{
	int res = -1;

	/* construct message plist */
	plist_t plist = create_plist_message("ReadBUID");

	res = send_plist_packet(sfd, tag, plist);
	plist_free(plist);

	return res;
}

static int send_pair_record_packet(int sfd, uint32_t tag, const char* msgtype, const char* pair_record_id, uint32_t device_id, plist_t data)
{
	int res = -1;

	/* construct message plist */
	plist_t plist = create_plist_message(msgtype);
	plist_dict_set_item(plist, "PairRecordID", plist_new_string(pair_record_id));
	if (data) {
		plist_dict_set_item(plist, "PairRecordData", plist_copy(data));
	}
	if (device_id > 0) {
		plist_dict_set_item(plist, "DeviceID", plist_new_uint(device_id));
	}

	res = send_plist_packet(sfd, tag, plist);
	plist_free(plist);

	return res;
}

/**
 * Generates an event, i.e. calls the callback function.
 * A reference to a populated usbmuxd_event_t with information about the event
 * and the corresponding device will be passed to the callback function.
 */
static void generate_event(const usbmuxd_device_info_t *dev, enum usbmuxd_event_type event)
{
	usbmuxd_event_t ev;

	if (!dev) {
		return;
	}

	ev.event = event;
	memcpy(&ev.device, dev, sizeof(usbmuxd_device_info_t));

	mutex_lock(&listener_mutex);
	FOREACH(struct usbmuxd_subscription_context* context, &listeners) {
		context->callback(&ev, context->user_data);
	} ENDFOREACH
	mutex_unlock(&listener_mutex);
}

static int usbmuxd_listen_poll()
{
	int sfd;

	sfd = connect_usbmuxd_socket();
	if (sfd < 0) {
		while (1) {
			mutex_lock(&listener_mutex);
			int num = collection_count(&listeners);
			mutex_unlock(&listener_mutex);
			if (num <= 0) {
				break;
			}
			if ((sfd = connect_usbmuxd_socket()) >= 0) {
				break;
			}
			sleep(1);
		}
	}

	return sfd;
}

#ifdef HAVE_INOTIFY
#ifndef HAVE_PSELECT
static int pselect(int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds, const struct timespec *timeout, const sigset_t *sigmask)
{
	int ready;
	struct timeval tv;
	struct timeval *p_timeout;
	sigset_t origmask;

	if (timeout) {
		tv.tv_sec = timeout->tv_sec;
		tv.tv_usec = timeout->tv_nsec / 1000;
		p_timeout = &tv;
	} else {
		p_timeout = NULL;
	}

	pthread_sigmask(SIG_SETMASK, sigmask, &origmask);
	ready = select(nfds, readfds, writefds, exceptfds, p_timeout);
	pthread_sigmask(SIG_SETMASK, &origmask, NULL);

	return ready;
}
#endif

static int usbmuxd_listen_inotify()
{
	int inot_fd;
	int watch_d;
	int sfd;

	if (!use_inotify) {
		return -2;
	}

	sfd = connect_usbmuxd_socket();
	if (sfd >= 0)
		return sfd;

	sfd = -1;
	inot_fd = inotify_init1(IN_CLOEXEC);
	if (inot_fd < 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Failed to setup inotify\n", __func__);
		return -2;
	}

	/* inotify is setup, listen for events that concern us */
	watch_d = inotify_add_watch (inot_fd, USBMUXD_DIRNAME, IN_CREATE);
	if (watch_d < 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Failed to setup watch descriptor for socket dir\n", __func__);
		close (inot_fd);
		return -2;
	}

	while (1) {
		fd_set rfds;
		struct timespec tv = {1, 0};

		FD_ZERO(&rfds);
		FD_SET(inot_fd, &rfds);
		int r = pselect(inot_fd+1, &rfds, NULL, NULL, &tv, NULL);
		if (r < 0) {
			break;
		}

		if (r == 0) {
			continue;
		}

		ssize_t len, i;
		char buff[EVENT_BUF_LEN] = {0};

		i = 0;
		len = read (inot_fd, buff, EVENT_BUF_LEN -1);
		if (len < 0)
			goto end;
		while (i < len) {
			struct inotify_event *pevent = (struct inotify_event *) & buff[i];

			/* check that it's ours */
			if (pevent->mask & IN_CREATE &&
				pevent->len &&
				pevent->name[0] != 0 &&
				strcmp(pevent->name, USBMUXD_SOCKET_NAME) == 0) {
				/* retry if usbmuxd isn't ready yet */
				int retry = 10;
				while (--retry >= 0) {
					if ((sfd = connect_usbmuxd_socket ()) >= 0) {
						break;
					}
					sleep(1);
				}
				goto end;
			}
			i += EVENT_SIZE + pevent->len;
		}
	}

end:
	inotify_rm_watch(inot_fd, watch_d);
	close(inot_fd);

	return sfd;
}
#endif /* HAVE_INOTIFY */

/**
 * Tries to connect to usbmuxd and wait if it is not running.
 */
static int usbmuxd_listen()
{
	int sfd;
	uint32_t res = -1;
	int tag;

retry:

#ifdef HAVE_INOTIFY
	sfd = usbmuxd_listen_inotify();
	if (sfd == -2)
		sfd = usbmuxd_listen_poll();
#else
	sfd = usbmuxd_listen_poll();
#endif

	if (sfd < 0) {
		if (!cancelling) {
			LIBUSBMUXD_DEBUG(1, "%s: ERROR: usbmuxd was supposed to be running here...\n", __func__);
		}
		return sfd;
	}

	tag = ++use_tag;
	if (send_listen_packet(sfd, tag) <= 0) {
		LIBUSBMUXD_DEBUG(1, "%s: ERROR: could not send listen packet\n", __func__);
		socket_close(sfd);
		return -1;
	}
	if ((usbmuxd_get_result(sfd, tag, &res, NULL) == 1) && (res != 0)) {
		socket_close(sfd);
		if ((res == RESULT_BADVERSION) && (proto_version == 1)) {
			proto_version = 0;
			goto retry;
		}
		LIBUSBMUXD_DEBUG(1, "%s: ERROR: did not get OK but %d\n", __func__, res);
		return -1;
	}
	return sfd;
}

/**
 * Waits for an event to occur, i.e. a packet coming from usbmuxd.
 * Calls generate_event to pass the event via callback to the client program.
 */
static int get_next_event(int sfd)
{
	struct usbmuxd_header hdr;
	void *payload = NULL;

	/* block until we receive something */
	if (receive_packet(sfd, &hdr, &payload, 0) < 0) {
		if (!cancelling) {
			LIBUSBMUXD_DEBUG(1, "%s: Error in usbmuxd connection, disconnecting all devices!\n", __func__);
		}
		// when then usbmuxd connection fails,
		// generate remove events for every device that
		// is still present so applications know about it
		FOREACH(usbmuxd_device_info_t *dev, &devices) {
			generate_event(dev, UE_DEVICE_REMOVE);
			collection_remove(&devices, dev);
			free(dev);
		} ENDFOREACH
		return -EIO;
	}

	if ((hdr.length > sizeof(hdr)) && !payload) {
		LIBUSBMUXD_DEBUG(1, "%s: Invalid packet received, payload is missing!\n", __func__);
		return -EBADMSG;
	}

	if (hdr.message == MESSAGE_DEVICE_ADD) {
		usbmuxd_device_info_t *devinfo = (usbmuxd_device_info_t*)payload;
		collection_add(&devices, devinfo);
		generate_event(devinfo, UE_DEVICE_ADD);
		payload = NULL;
	} else if (hdr.message == MESSAGE_DEVICE_REMOVE) {
		uint32_t handle;
		usbmuxd_device_info_t *devinfo;

		memcpy(&handle, payload, sizeof(uint32_t));

		devinfo = devices_find(handle);
		if (!devinfo) {
			LIBUSBMUXD_DEBUG(1, "%s: WARNING: got device remove message for handle %d, but couldn't find the corresponding handle in the device list. This event will be ignored.\n", __func__, handle);
		} else {
			generate_event(devinfo, UE_DEVICE_REMOVE);
			collection_remove(&devices, devinfo);
			free(devinfo);
		}
	} else if (hdr.message == MESSAGE_DEVICE_PAIRED) {
		uint32_t handle;
		usbmuxd_device_info_t *devinfo;

		memcpy(&handle, payload, sizeof(uint32_t));

		devinfo = devices_find(handle);
		if (!devinfo) {
			LIBUSBMUXD_DEBUG(1, "%s: WARNING: got paired message for device handle %d, but couldn't find the corresponding handle in the device list. This event will be ignored.\n", __func__, handle);
		} else {
			generate_event(devinfo, UE_DEVICE_PAIRED);
		}
	} else if (hdr.length > 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Unexpected message type %d length %d received!\n", __func__, hdr.message, hdr.length);
	}
	free(payload);
	return 0;
}

static void device_monitor_cleanup(void* data)
{
	FOREACH(usbmuxd_device_info_t *dev, &devices) {
		collection_remove(&devices, dev);
		free(dev);
	} ENDFOREACH
	collection_free(&devices);

	socket_close(listenfd);
	listenfd = -1;
}

/**
 * Device Monitor thread function.
 *
 * This function sets up a connection to usbmuxd
 */
static void *device_monitor(void *data)
{
	running = 1;
	collection_init(&devices);
	cancelling = 0;

#ifdef HAVE_THREAD_CLEANUP
	thread_cleanup_push(device_monitor_cleanup, NULL);
#endif
	do {

		listenfd = usbmuxd_listen();
		if (listenfd < 0) {
			continue;
		}

		while (running) {
			int res = get_next_event(listenfd);
			if (res < 0) {
				break;
			}
		}

		mutex_lock(&listener_mutex);
		if (collection_count(&listeners) == 0) {
			running = 0;
		}
		mutex_unlock(&listener_mutex);
	} while (running);

#ifdef HAVE_THREAD_CLEANUP
	thread_cleanup_pop(1);
#else
	device_monitor_cleanup(NULL);
#endif

	return NULL;
}

static void init_listeners(void)
{
	collection_init(&listeners);
	mutex_init(&listener_mutex);
}

int usbmuxd_events_subscribe(usbmuxd_subscription_context_t *context, usbmuxd_event_cb_t callback, void *user_data)
{
	if (!context || !callback) {
		return -EINVAL;
	}

	thread_once(&listener_init_once, init_listeners);

	mutex_lock(&listener_mutex);
	*context = malloc(sizeof(struct usbmuxd_subscription_context));
	if (!*context) {
		mutex_unlock(&listener_mutex);
		LIBUSBMUXD_ERROR("ERROR: %s: malloc failed\n", __func__);
		return -ENOMEM;
	}
	(*context)->callback = callback;
	(*context)->user_data = user_data;

	collection_add(&listeners, *context);

	if (devmon == THREAD_T_NULL || !thread_alive(devmon)) {
		mutex_unlock(&listener_mutex);
		int res = thread_new(&devmon, device_monitor, NULL);
		if (res != 0) {
			free(*context);
			LIBUSBMUXD_DEBUG(1, "%s: ERROR: Could not start device watcher thread!\n", __func__);
			return res;
		}
	} else {
		/* we need to submit DEVICE_ADD events to the new listener */
		FOREACH(usbmuxd_device_info_t *dev, &devices) {
			if (dev) {
				usbmuxd_event_t ev;
				ev.event = UE_DEVICE_ADD;
				memcpy(&ev.device, dev, sizeof(usbmuxd_device_info_t));
				(*context)->callback(&ev, (*context)->user_data);
			}
		} ENDFOREACH
		mutex_unlock(&listener_mutex);
	}

	return 0;
}

int usbmuxd_events_unsubscribe(usbmuxd_subscription_context_t context)
{
	int ret = 0;
	int num = 0;

	if (!context) {
		return -EINVAL;
	}

	mutex_lock(&listener_mutex);
	if (collection_remove(&listeners, context) == 0) {
		FOREACH(usbmuxd_device_info_t *dev, &devices) {
			if (dev) {
				usbmuxd_event_t ev;
				ev.event = UE_DEVICE_REMOVE;
				memcpy(&ev.device, dev, sizeof(usbmuxd_device_info_t));
				(context)->callback(&ev, (context)->user_data);
			}
		} ENDFOREACH
		free(context);
	}
	num = collection_count(&listeners);
	mutex_unlock(&listener_mutex);

	if (num == 0) {
		int res = 0;
		cancelling = 1;
		socket_shutdown(listenfd, SHUT_RDWR);
		if (thread_alive(devmon)) {
			if (thread_cancel(devmon) < 0) {
				running = 0;
			}
#if defined(HAVE_INOTIFY) && !defined(HAVE_PTHREAD_CANCEL)
			pthread_kill(devmon, SIGINT);
#endif
			res = thread_join(devmon);
			thread_free(devmon);
			devmon = THREAD_T_NULL;
		}
		if ((res != 0) && (res != ESRCH)) {
			ret = res;
		}
	}

	return ret;
}

int usbmuxd_subscribe(usbmuxd_event_cb_t callback, void *user_data)
{
	if (!callback) {
		return -EINVAL;
	}

	if (event_ctx) {
		usbmuxd_events_unsubscribe(event_ctx);
		event_ctx = NULL;
	}
	return usbmuxd_events_subscribe(&event_ctx, callback, user_data);
}

int usbmuxd_unsubscribe(void)
{
	int res = usbmuxd_events_unsubscribe(event_ctx);
	event_ctx = NULL;
	return res;
}

int usbmuxd_get_device_list(usbmuxd_device_info_t **device_list)
{
	int sfd;
	int tag;
	int listen_success = 0;
	uint32_t res;
	struct collection tmpdevs;
	usbmuxd_device_info_t *newlist = NULL;
	struct usbmuxd_header hdr;
	int dev_cnt = 0;
	void *payload = NULL;

	*device_list = NULL;

retry:
	sfd = connect_usbmuxd_socket();
	if (sfd < 0) {
		LIBUSBMUXD_DEBUG(1, "%s: error opening socket!\n", __func__);
		return sfd;
	}

	tag = ++use_tag;
	if ((proto_version == 1) && (try_list_devices)) {
		if (send_list_devices_packet(sfd, tag) > 0) {
			plist_t list = NULL;
			if ((usbmuxd_get_result(sfd, tag, &res, &list) == 1) && (res == 0)) {
				plist_t devlist = plist_dict_get_item(list, "DeviceList");
				if (devlist && plist_get_node_type(devlist) == PLIST_ARRAY) {
					collection_init(&tmpdevs);
					uint32_t numdevs = plist_array_get_size(devlist);
					uint32_t i;
					for (i = 0; i < numdevs; i++) {
						plist_t pdev = plist_array_get_item(devlist, i);
						plist_t props = plist_dict_get_item(pdev, "Properties");
						usbmuxd_device_info_t *devinfo = device_info_from_plist(props);
						if (!devinfo) {
							socket_close(sfd);
							LIBUSBMUXD_DEBUG(1, "%s: Could not create device info object from properties!\n", __func__);
							plist_free(list);
							return -1;
						}
						collection_add(&tmpdevs, devinfo);
					}
					plist_free(list);
					goto got_device_list;
				}
			} else {
				if (res == RESULT_BADVERSION) {
					proto_version = 0;
				}
				socket_close(sfd);
				try_list_devices = 0;
				plist_free(list);
				goto retry;
			}
			plist_free(list);
		}
	}

	tag = ++use_tag;
	if (send_listen_packet(sfd, tag) > 0) {
		res = -1;
		// get response
		if ((usbmuxd_get_result(sfd, tag, &res, NULL) == 1) && (res == 0)) {
			listen_success = 1;
		} else {
			socket_close(sfd);
			if ((res == RESULT_BADVERSION) && (proto_version == 1)) {
				proto_version = 0;
				goto retry;
			}
			LIBUSBMUXD_DEBUG(1, "%s: Did not get response to scan request (with result=0)...\n", __func__);
			return res;
		}
	}

	if (!listen_success) {
		socket_close(sfd);
		LIBUSBMUXD_DEBUG(1, "%s: Could not send listen request!\n", __func__);
		return -1;
	}

	collection_init(&tmpdevs);

	// receive device list
	while (1) {
		if (receive_packet(sfd, &hdr, &payload, 100) > 0) {
			if (hdr.message == MESSAGE_DEVICE_ADD) {
				usbmuxd_device_info_t *devinfo = payload;
				collection_add(&tmpdevs, devinfo);
				payload = NULL;
			} else if (hdr.message == MESSAGE_DEVICE_REMOVE) {
				uint32_t handle;
				usbmuxd_device_info_t *devinfo = NULL;

				memcpy(&handle, payload, sizeof(uint32_t));

				FOREACH(usbmuxd_device_info_t *di, &tmpdevs) {
					if (di && di->handle == handle) {
						devinfo = di;
						break;
					}
				} ENDFOREACH
				if (devinfo) {
					collection_remove(&tmpdevs, devinfo);
					free(devinfo);
				}
			} else {
				LIBUSBMUXD_DEBUG(1, "%s: Unexpected message %d\n", __func__, hdr.message);
			}
			free(payload);
		} else {
			// we _should_ have all of them now.
			// or perhaps an error occurred.
			break;
		}
	}

got_device_list:

	// explicitly close connection
	socket_close(sfd);

	// create copy of device info entries from collection
	newlist = (usbmuxd_device_info_t*)malloc(sizeof(usbmuxd_device_info_t) * (collection_count(&tmpdevs) + 1));
	dev_cnt = 0;
	FOREACH(usbmuxd_device_info_t *di, &tmpdevs) {
		if (di) {
			memcpy(&newlist[dev_cnt], di, sizeof(usbmuxd_device_info_t));
			free(di);
			dev_cnt++;
		}
	} ENDFOREACH
	collection_free(&tmpdevs);

	memset(&newlist[dev_cnt], 0, sizeof(usbmuxd_device_info_t));
	*device_list = newlist;

	return dev_cnt;
}

int usbmuxd_device_list_free(usbmuxd_device_info_t **device_list)
{
	if (device_list) {
		free(*device_list);
	}
	return 0;
}

int usbmuxd_get_device_by_udid(const char *udid, usbmuxd_device_info_t *device)
{
	usbmuxd_device_info_t *dev_list = NULL;
	usbmuxd_device_info_t *dev = NULL;
	int result = 0;
	int i;

	if (!device) {
		return -EINVAL;
	}
	if (usbmuxd_get_device_list(&dev_list) < 0) {
		return -ENODEV;
	}

	for (i = 0; dev_list[i].handle > 0; i++) {
	 	if (!udid) {
			if (dev_list[i].conn_type == CONNECTION_TYPE_USB) {
				dev = &dev_list[i];
				break;
			}
		} else if (!strcmp(udid, dev_list[i].udid)) {
			if (dev_list[i].conn_type == CONNECTION_TYPE_USB) {
				dev = &dev_list[i];
				break;
			}
		}
	}

	if (dev) {
		device->handle = dev->handle;
		device->product_id = dev->product_id;
		char *t = stpncpy(device->udid, dev->udid, sizeof(device->udid)-1);
		*t = '\0';
		device->conn_type = dev->conn_type;
		memcpy(device->conn_data, dev->conn_data, sizeof(device->conn_data));
		result = 1;
	}

	usbmuxd_device_list_free(&dev_list);

	return result;
}

int usbmuxd_get_device(const char *udid, usbmuxd_device_info_t *device, enum usbmux_lookup_options options)
{
	usbmuxd_device_info_t *dev_list = NULL;
	usbmuxd_device_info_t *dev_network = NULL;
	usbmuxd_device_info_t *dev_usbmuxd = NULL;
	usbmuxd_device_info_t *dev = NULL;
	int result = 0;
	int i;

	if (!device) {
		return -EINVAL;
	}
	if (usbmuxd_get_device_list(&dev_list) < 0) {
		return -ENODEV;
	}

	if (options == 0) {
		options = DEVICE_LOOKUP_USBMUX;
	}

	for (i = 0; dev_list[i].handle > 0; i++) {
		if (!udid) {
			if ((options & DEVICE_LOOKUP_USBMUX) && (dev_list[i].conn_type == CONNECTION_TYPE_USB)) {
				dev_usbmuxd = &dev_list[i];
				break;
			}
			if ((options & DEVICE_LOOKUP_NETWORK) && (dev_list[i].conn_type == CONNECTION_TYPE_NETWORK)) {
				dev_network = &dev_list[i];
				break;
			}
		} else if (!strcmp(udid, dev_list[i].udid)) {
			if ((options & DEVICE_LOOKUP_USBMUX) && (dev_list[i].conn_type == CONNECTION_TYPE_USB)) {
				dev_usbmuxd = &dev_list[i];
			} else if ((options & DEVICE_LOOKUP_NETWORK) && (dev_list[i].conn_type == CONNECTION_TYPE_NETWORK)) {
				dev_network = &dev_list[i];
			}
		}
		if (dev_usbmuxd && dev_network) {
			break;
		}
	}

	if (dev_network && dev_usbmuxd) {
		dev = (options & DEVICE_LOOKUP_PREFER_NETWORK) ? dev_network : dev_usbmuxd;
	} else if (dev_network) {
		dev = dev_network;
	} else if (dev_usbmuxd) {
		dev = dev_usbmuxd;
	}

	if (dev) {
		device->handle = dev->handle;
		device->product_id = dev->product_id;
		char *t = stpncpy(device->udid, dev->udid, sizeof(device->udid)-1);
		*t = '\0';
		device->conn_type = dev->conn_type;
		memcpy(device->conn_data, dev->conn_data, sizeof(device->conn_data));
		result = 1;
	}

	free(dev_list);

	return result;
}

int usbmuxd_connect(const uint32_t handle, const unsigned short port)
{
	int sfd;
	int tag;
	int connected = 0;
	int result = EBADF;

retry:
	sfd = connect_usbmuxd_socket();
	if (sfd < 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Error: Connection to usbmuxd failed: %s\n", __func__, strerror(-sfd));
		return sfd;
	}

	tag = ++use_tag;
	if (send_connect_packet(sfd, tag, handle, (uint16_t)port) <= 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Error sending connect message!\n", __func__);
	} else {
		// read ACK
		uint32_t res = -1;
		LIBUSBMUXD_DEBUG(2, "%s: Reading connect result...\n", __func__);
		if (usbmuxd_get_result(sfd, tag, &res, NULL) == 1) {
			if (res == 0) {
				LIBUSBMUXD_DEBUG(2, "%s: Connect success!\n", __func__);
				connected = 1;
			} else {
				if ((res == RESULT_BADVERSION) && (proto_version == 1)) {
					proto_version = 0;
					socket_close(sfd);
					goto retry;
				}
				LIBUSBMUXD_DEBUG(1, "%s: Connect failed, Error code=%d\n", __func__, res);
				if (res == RESULT_CONNREFUSED) {
					result = ECONNREFUSED;
				} else if (res == RESULT_BADDEV) {
					result = ENODEV;
				} else {
					result = EBADF;
				}
			}
		}
	}

	if (connected) {
		return sfd;
	}

	socket_close(sfd);

	return -result;
}

int usbmuxd_disconnect(int sfd)
{
	return socket_close(sfd);
}

int usbmuxd_send(int sfd, const char *data, uint32_t len, uint32_t *sent_bytes)
{
	int num_sent;

	if (sfd < 0) {
		return -EINVAL;
	}

	num_sent = socket_send(sfd, (void*)data, len);
	if (num_sent < 0) {
		*sent_bytes = 0;
		LIBUSBMUXD_DEBUG(1, "%s: Error %d when sending: %s\n", __func__, -num_sent, strerror(-num_sent));
		return num_sent;
	}

	if ((uint32_t)num_sent < len) {
		LIBUSBMUXD_DEBUG(1, "%s: Warning: Did not send enough (only %d of %d)\n", __func__, num_sent, len);
	}

	*sent_bytes = num_sent;

	return 0;
}

int usbmuxd_recv_timeout(int sfd, char *data, uint32_t len, uint32_t *recv_bytes, unsigned int timeout)
{
	int num_recv = socket_receive_timeout(sfd, (void*)data, len, 0, timeout);
	if (num_recv < 0) {
		*recv_bytes = 0;
		return num_recv;
	}

	*recv_bytes = num_recv;

	return 0;
}

int usbmuxd_recv(int sfd, char *data, uint32_t len, uint32_t *recv_bytes)
{
	return usbmuxd_recv_timeout(sfd, data, len, recv_bytes, 5000);
}

int usbmuxd_read_buid(char **buid)
{
	int sfd;
	int tag;
	int ret = -1;

	if (!buid) {
		return -EINVAL;
	}
	*buid = NULL;

	sfd = connect_usbmuxd_socket();
	if (sfd < 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Error: Connection to usbmuxd failed: %s\n", __func__, strerror(-sfd));
		return sfd;
	}

	proto_version = 1;
	tag = ++use_tag;
	if (send_read_buid_packet(sfd, tag) <= 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Error sending ReadBUID message!\n", __func__);
	} else {
		uint32_t rc = 0;
		plist_t pl = NULL;
		ret = usbmuxd_get_result(sfd, tag, &rc, &pl);
		if ((ret == 1) && (rc == 0)) {
			plist_t node = plist_dict_get_item(pl, "BUID");
			if (node && plist_get_node_type(node) == PLIST_STRING) {
				plist_get_string_val(node, buid);
			}
			ret = 0;
		} else if (ret == 1) {
			ret = -(int)rc;
		}
		plist_free(pl);
	}
	socket_close(sfd);

	return ret;
}

int usbmuxd_read_pair_record(const char* record_id, char **record_data, uint32_t *record_size)
{
	int sfd;
	int tag;
	int ret = -1;

	if (!record_id || !record_data || !record_size) {
		return -EINVAL;
	}
	*record_data = NULL;
	*record_size = 0;

	sfd = connect_usbmuxd_socket();
	if (sfd < 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Error: Connection to usbmuxd failed: %s\n", __func__, strerror(-sfd));
		return sfd;
	}

	proto_version = 1;
	tag = ++use_tag;

	if (send_pair_record_packet(sfd, tag, "ReadPairRecord", record_id, 0, NULL) <= 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Error sending ReadPairRecord message!\n", __func__);
	} else {
		uint32_t rc = 0;
		plist_t pl = NULL;
		ret = usbmuxd_get_result(sfd, tag, &rc, &pl);
		if ((ret == 1) && (rc == 0)) {
			plist_t node = plist_dict_get_item(pl, "PairRecordData");
			if (node && plist_get_node_type(node) == PLIST_DATA) {
				uint64_t int64val = 0;
				plist_get_data_val(node, record_data, &int64val);
				if (*record_data && int64val > 0) {
					*record_size = (uint32_t)int64val;
					ret = 0;
				}
			}
		} else if (ret == 1) {
			ret = -(int)rc;
		}
		plist_free(pl);
	}
	socket_close(sfd);

	return ret;
}

int usbmuxd_save_pair_record_with_device_id(const char* record_id, uint32_t device_id, const char *record_data, uint32_t record_size)
{
	int sfd;
	int tag;
	int ret = -1;

	if (!record_id || !record_data || !record_size) {
		return -EINVAL;
	}

	sfd = connect_usbmuxd_socket();
	if (sfd < 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Error: Connection to usbmuxd failed: %s\n", __func__, strerror(-sfd));
		return sfd;
	}

	proto_version = 1;
	tag = ++use_tag;

	plist_t data = plist_new_data(record_data, record_size);
	if (send_pair_record_packet(sfd, tag, "SavePairRecord", record_id, device_id, data) <= 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Error sending SavePairRecord message!\n", __func__);
	} else {
		uint32_t rc = 0;
		ret = usbmuxd_get_result(sfd, tag, &rc, NULL);
		if ((ret == 1) && (rc == 0)) {
			ret = 0;
		} else if (ret == 1) {
			ret = -(int)rc;
			LIBUSBMUXD_DEBUG(1, "%s: Error: saving pair record failed: %d\n", __func__, ret);
		}
	}
	plist_free(data);
	socket_close(sfd);

	return ret;
}

int usbmuxd_save_pair_record(const char* record_id, const char *record_data, uint32_t record_size)
{
	return usbmuxd_save_pair_record_with_device_id(record_id, 0, record_data, record_size);
}

int usbmuxd_delete_pair_record(const char* record_id)
{
	int sfd;
	int tag;
	int ret = -1;

	if (!record_id) {
		return -EINVAL;
	}

	sfd = connect_usbmuxd_socket();
	if (sfd < 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Error: Connection to usbmuxd failed: %s\n", __func__, strerror(-sfd));
		return sfd;
	}

	proto_version = 1;
	tag = ++use_tag;

	if (send_pair_record_packet(sfd, tag, "DeletePairRecord", record_id, 0, NULL) <= 0) {
		LIBUSBMUXD_DEBUG(1, "%s: Error sending DeletePairRecord message!\n", __func__);
	} else {
		uint32_t rc = 0;
		ret = usbmuxd_get_result(sfd, tag, &rc, NULL);
		if ((ret == 1) && (rc == 0)) {
			ret = 0;
		} else if (ret == 1) {
			ret = -(int)rc;
			LIBUSBMUXD_DEBUG(1, "%s: Error: deleting pair record failed: %d\n", __func__, ret);
		}
	}
	socket_close(sfd);

	return ret;
}

void libusbmuxd_set_use_inotify(int set)
{
#ifdef HAVE_INOTIFY
	use_inotify = set;
#endif
}

void libusbmuxd_set_debug_level(int level)
{
	libusbmuxd_debug = level;
	socket_set_verbose(level);
}

const char* libusbmuxd_version()
{
#ifndef PACKAGE_VERSION
#error PACKAGE_VERSION is not defined
#endif
	return PACKAGE_VERSION;
}
