summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--iphone.c49
-rw-r--r--iphone.h3
-rw-r--r--main.c128
3 files changed, 86 insertions, 94 deletions
diff --git a/iphone.c b/iphone.c
index ad9dafd..5cceb95 100644
--- a/iphone.c
+++ b/iphone.c
@@ -114,7 +114,13 @@ static int clients = 0;
/**
*/
-int toto_debug = 1;
+int toto_debug = 0;
+
+void iphone_set_debug(int e)
+{
+ toto_debug = e;
+}
+
void log_debug_msg(const char *format, ...)
{
#ifndef STRIP_DEBUG_CODE
@@ -518,13 +524,11 @@ int send_to_phone(iphone_device_t phone, char *data, int datalen)
*/
int recv_from_phone_timeout(iphone_device_t phone, char *data, int datalen, int timeoutmillis)
{
- if (!phone)
- return -1;
int bytes = 0;
if (!phone)
- return -1;
- log_debug_msg("recv_from_phone(): attempting to receive %i bytes\n", datalen);
+ return -EINVAL;
+ //log_debug_msg("recv_from_phone(): attempting to receive %i bytes\n", datalen);
bytes = usb_bulk_read(phone->device, BULKIN, data, datalen, timeoutmillis);
if (bytes < 0) {
@@ -534,6 +538,7 @@ int recv_from_phone_timeout(iphone_device_t phone, char *data, int datalen, int
if (bytes == -ETIMEDOUT) {
// ignore this. it just means timeout reached before we
// picked up any data. no problem.
+ return 0;
}
else {
fprintf(stderr, "recv_from_phone(): libusb gave me the error %d: %s (%s)\n", bytes, usb_strerror(),
@@ -541,7 +546,7 @@ int recv_from_phone_timeout(iphone_device_t phone, char *data, int datalen, int
log_debug_msg("recv_from_phone(): libusb gave me the error %d: %s (%s)\n", bytes, usb_strerror(),
strerror(-bytes));
}
- return -1;
+ return bytes;
}
#ifdef DEBUG
@@ -736,7 +741,7 @@ iphone_error_t iphone_mux_new_client(iphone_device_t device, uint16_t src_port,
add_connection(new_connection);
new_connection->error = IPHONE_E_SUCCESS;
hton_header(new_connection->header);
- printf("%s: send_to_phone (%d --> %d)\n", __func__, ntohs(new_connection->header->sport), ntohs(new_connection->header->dport));
+ log_debug_msg("%s: send_to_phone (%d --> %d)\n", __func__, ntohs(new_connection->header->sport), ntohs(new_connection->header->dport));
if (send_to_phone(device, (char *) new_connection->header, sizeof(usbmux_tcp_header)) >= 0) {
*client = new_connection;
return IPHONE_E_SUCCESS;
@@ -842,7 +847,7 @@ iphone_error_t iphone_mux_send(iphone_umux_client_t client, const char *data, ui
memcpy(buffer, client->header, sizeof(usbmux_tcp_header));
memcpy(buffer + sizeof(usbmux_tcp_header), data, datalen);
- printf("%s: send_to_phone(%d --> %d)\n", __func__, ntohs(client->header->sport), ntohs(client->header->dport));
+ log_debug_msg("%s: send_to_phone(%d --> %d)\n", __func__, ntohs(client->header->sport), ntohs(client->header->dport));
sendresult = send_to_phone(client->phone, buffer, blocksize);
// Now that we've sent it off, we can clean up after our sloppy selves.
if (buffer)
@@ -907,9 +912,9 @@ uint32 append_receive_buffer(iphone_umux_client_t client, char* packet)
// falls on our responsibility because we are the ones reading in
// feedback.
if (client->header->scnt == 0 && client->header->ocnt == 0 ) {
- fprintf(stdout, "client is still waiting for handshake.\n");
+ log_debug_msg("client is still waiting for handshake.\n");
if (header->tcp_flags == (TCP_SYN | TCP_ACK)) {
- fprintf(stdout, "yes, got syn+ack ; replying with ack.\n");
+ log_debug_msg("yes, got syn+ack ; replying with ack.\n");
client->header->tcp_flags = TCP_ACK;
client->header->length = sizeof(usbmux_tcp_header);
client->header->length16 = sizeof(usbmux_tcp_header);
@@ -918,9 +923,9 @@ uint32 append_receive_buffer(iphone_umux_client_t client, char* packet)
hton_header(client->header);
// push it to USB
// TODO: need to check for error in the send here.... :(
- printf("%s: send_to_phone (%d --> %d)\n", __func__, ntohs(client->header->sport), ntohs(client->header->dport));
+ log_debug_msg("%s: send_to_phone (%d --> %d)\n", __func__, ntohs(client->header->sport), ntohs(client->header->dport));
if (send_to_phone(client->phone, (char *)client->header, sizeof(usbmux_tcp_header)) <= 0) {
- fprintf(stdout, "%s: error when pushing to usb...\n", __func__);
+ log_debug_msg("%s: error when pushing to usb...\n", __func__);
}
// need to revert some of the fields back to host notation.
ntoh_header(client->header);
@@ -929,7 +934,7 @@ uint32 append_receive_buffer(iphone_umux_client_t client, char* packet)
client->error = IPHONE_E_ECONNABORTED;
// woah... this connection failed us.
// TODO: somehow signal that this stream is a no-go.
- fprintf(stderr, "WOAH! client failed to get proper syn+ack.\n");
+ log_debug_msg("WOAH! client failed to get proper syn+ack.\n");
}
}
@@ -1002,7 +1007,7 @@ uint32 append_receive_buffer(iphone_umux_client_t client, char* packet)
// ensure there is enough space, either by first malloc or realloc
if (datalen > 0) {
- fprintf(stderr, "%s: putting %d bytes into client's recv_buffer\n", __func__, datalen);
+ log_debug_msg("%s: putting %d bytes into client's recv_buffer\n", __func__, datalen);
if (client->r_len == 0) dobroadcast = 1;
if (client->recv_buffer == NULL) {
@@ -1061,13 +1066,14 @@ iphone_umux_client_t find_client(usbmux_tcp_header* recv_header)
/** pull in a big USB bulk packet and distribute it to queues appropriately.
*/
-void iphone_mux_pullbulk(iphone_device_t phone)
+int iphone_mux_pullbulk(iphone_device_t phone)
{
if (!phone) {
fprintf(stderr, "iphone_mux_pullbulk: invalid argument\n");
- return;
+ return -EINVAL;
}
+ int res = 0;
static const int DEFAULT_CAPACITY = 128*1024;
if (phone->usbReceive.buffer == NULL) {
phone->usbReceive.capacity = DEFAULT_CAPACITY;
@@ -1080,6 +1086,7 @@ void iphone_mux_pullbulk(iphone_device_t phone)
// pull in content, note that the amount we can pull is capacity minus leftover
int readlen = recv_from_phone_timeout(phone, cursor, phone->usbReceive.capacity - phone->usbReceive.leftover, 5000);
if (readlen < 0) {
+ res = readlen;
//fprintf(stderr, "recv_from_phone_timeout gave us an error.\n");
readlen = 0;
}
@@ -1099,24 +1106,24 @@ void iphone_mux_pullbulk(iphone_device_t phone)
if (phone->usbReceive.leftover < HEADERLEN) break;
usbmux_tcp_header *header = (usbmux_tcp_header *) cursor;
- printf("%s: recv_from_phone_timeout (%d --> %d)\n", __func__, ntohs(header->sport), ntohs(header->dport));
+ log_debug_msg("%s: recv_from_phone_timeout (%d --> %d)\n", __func__, ntohs(header->sport), ntohs(header->dport));
// now that we have a header, check if there is sufficient data
// to construct a full packet, including its data
uint32 packetlen = ntohl(header->length);
if (phone->usbReceive.leftover < packetlen) {
- printf("%s: not enough data to construct a full packet\n", __func__);
+ fprintf(stderr, "%s: not enough data to construct a full packet\n", __func__);
break;
}
// ok... find the client this packet will get stuffed to.
iphone_umux_client_t client = find_client(header);
if (client == NULL) {
- fprintf(stderr, "WARNING: client for packet cannot be found. dropping packet.\n");
+ log_debug_msg("WARNING: client for packet cannot be found. dropping packet.\n");
}
else {
// stuff the data
- fprintf(stderr, "%s: found client, calling append_receive_buffer\n", __func__);
+ log_debug_msg("%s: found client, calling append_receive_buffer\n", __func__);
append_receive_buffer(client, cursor);
}
@@ -1141,6 +1148,8 @@ void iphone_mux_pullbulk(iphone_device_t phone)
phone->usbReceive.buffer = newbuff;
phone->usbReceive.capacity = DEFAULT_CAPACITY;
}
+
+ return res;
}
/**
diff --git a/iphone.h b/iphone.h
index e132cd5..fcef32a 100644
--- a/iphone.h
+++ b/iphone.h
@@ -50,6 +50,7 @@
#define IPHONE_E_ETIMEDOUT -ETIMEDOUT
#define IPHONE_E_ECONNREFUSED -ECONNREFUSED
+void iphone_set_debug(int e);
typedef int16_t iphone_error_t;
@@ -72,7 +73,7 @@ iphone_error_t iphone_mux_send(iphone_umux_client_t client, const char *data, ui
iphone_error_t iphone_mux_recv(iphone_umux_client_t client, char *data, uint32_t datalen, uint32_t * recv_bytes);
iphone_error_t iphone_mux_recv_timeout(iphone_umux_client_t client, char *data, uint32_t datalen, uint32_t * recv_bytes, int timeout);
-void iphone_mux_pullbulk(iphone_device_t phone);
+int iphone_mux_pullbulk(iphone_device_t phone);
iphone_error_t iphone_mux_get_error(iphone_umux_client_t client);
diff --git a/main.c b/main.c
index c0bb340..6b1b6ce 100644
--- a/main.c
+++ b/main.c
@@ -55,7 +55,7 @@ static int verbose = DEBUG_LEVEL;
static int foreground = 0;
static int exit_on_no_devices = 0;
-struct device_use_info {
+struct device_info {
uint32_t device_id;
iphone_device_t phone;
int use_count;
@@ -78,11 +78,11 @@ struct client_data {
int handler_dead;
int connected;
iphone_umux_client_t muxclient;
- struct device_use_info *duinfo;
+ struct device_info *dev;
};
-static struct device_use_info **device_use_list = NULL;
-static int device_use_count = 0;
+static struct device_info **devices = NULL;
+static int device_count = 0;
static pthread_mutex_t usbmux_mutex = PTHREAD_MUTEX_INITIALIZER;
static pthread_mutex_t usb_mutex = PTHREAD_MUTEX_INITIALIZER;
@@ -223,7 +223,7 @@ static void *usbmuxd_client_reader_thread(void *arg)
cdata->reader_dead = 0;
- if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: started\n", __func__, cdata->duinfo->device_id, cdata->duinfo->use_count);
+ if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: started\n", __func__, cdata->dev->device_id, cdata->dev->use_count);
while (!quit_flag && !cdata->reader_quit) {
result = check_fd(cdata->socket, FD_WRITE, DEFAULT_TIMEOUT);
@@ -237,7 +237,7 @@ static void *usbmuxd_client_reader_thread(void *arg)
rlen = 0;
err = iphone_mux_recv_timeout(cdata->muxclient, rbuffer, rbuffersize, &rlen, DEFAULT_TIMEOUT);
if (err != 0) {
- if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: encountered USB read error: %d\n", __func__, cdata->duinfo->device_id, cdata->duinfo->use_count, err);
+ if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: encountered USB read error: %d\n", __func__, cdata->dev->device_id, cdata->dev->use_count, err);
break;
}
@@ -261,7 +261,7 @@ static void *usbmuxd_client_reader_thread(void *arg)
fsync(cdata->socket);
}
- if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: terminated\n", __func__, cdata->duinfo->device_id, cdata->duinfo->use_count);
+ if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: terminated\n", __func__, cdata->dev->device_id, cdata->dev->use_count);
cdata->reader_dead = 1;
@@ -358,7 +358,7 @@ static void *usbmuxd_client_handler_thread(void *arg)
cdata = (struct client_data*)arg;
- if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: started\n", __func__, cdata->duinfo->device_id,cdata->duinfo->use_count);
+ if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: started\n", __func__, cdata->dev->device_id,cdata->dev->use_count);
if (usbmuxd_handleConnectResult(cdata)) {
if (verbose >= 3) fprintf(stderr, "handleConnectResult: Error\n");
@@ -391,20 +391,20 @@ static void *usbmuxd_client_handler_thread(void *arg)
break;
}
if (len < 0) {
- if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: Error: recv: %s\n", __func__, cdata->duinfo->device_id, cdata->duinfo->use_count, strerror(errno));
+ if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: Error: recv: %s\n", __func__, cdata->dev->device_id, cdata->dev->use_count, strerror(errno));
break;
}
cursor = buffer;
- pthread_mutex_lock(&cdata->duinfo->writer_mutex);
+ pthread_mutex_lock(&cdata->dev->writer_mutex);
do {
wlen = 0;
err = iphone_mux_send(cdata->muxclient, cursor, len, &wlen);
if (err == IPHONE_E_TIMEOUT) {
// some kind of timeout... just be patient and retry.
} else if (err != IPHONE_E_SUCCESS) {
- if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: USB write error: %d\n", __func__, cdata->duinfo->device_id, cdata->duinfo->use_count, err);
+ if (verbose >= 2) fprintf(stderr, "%s[%d:%d]: USB write error: %d\n", __func__, cdata->dev->device_id, cdata->dev->use_count, err);
len = -1;
break;
}
@@ -414,7 +414,7 @@ static void *usbmuxd_client_handler_thread(void *arg)
// advance cursor appropiately.
cursor += wlen;
} while ((len > 0) && !quit_flag);
- pthread_mutex_unlock(&cdata->duinfo->writer_mutex);
+ pthread_mutex_unlock(&cdata->dev->writer_mutex);
if (len < 0) {
break;
}
@@ -422,7 +422,7 @@ static void *usbmuxd_client_handler_thread(void *arg)
leave:
// cleanup
- if (verbose >= 3) fprintf(stderr, "%s[%d:%d]: terminating\n", __func__, cdata->duinfo->device_id, cdata->duinfo->use_count);
+ if (verbose >= 3) fprintf(stderr, "%s[%d:%d]: terminating\n", __func__, cdata->dev->device_id, cdata->dev->use_count);
if (cdata->reader != 0) {
cdata->reader_quit = 1;
pthread_join(cdata->reader, NULL);
@@ -430,7 +430,7 @@ leave:
cdata->handler_dead = 1;
- if (verbose >= 3) fprintf(stderr, "%s[%d:%d]: terminated\n", __func__, cdata->duinfo->device_id, cdata->duinfo->use_count);
+ if (verbose >= 3) fprintf(stderr, "%s[%d:%d]: terminated\n", __func__, cdata->dev->device_id, cdata->dev->use_count);
return NULL;
}
@@ -440,14 +440,15 @@ leave:
*/
static void *usbmuxd_bulk_reader_thread(void *arg)
{
- struct device_use_info *cur_dev;
+ struct device_info *cur_dev;
+ int err;
if (!arg) {
if (verbose >= 3) fprintf(stderr, "%s: Invalid client_data provided\n", __func__);
return NULL;
}
- cur_dev = (struct device_use_info*)arg;
+ cur_dev = (struct device_info*)arg;
if (verbose >= 5) fprintf(stderr, "%s: started\n", __func__);
@@ -460,11 +461,10 @@ static void *usbmuxd_bulk_reader_thread(void *arg)
}
pthread_mutex_unlock(&cur_dev->mutex);
- iphone_mux_pullbulk(cur_dev->phone);
- //err = iphone_mux_get_error(cdata->muxclient);
- //if (err != IPHONE_E_SUCCESS) {
- // break;
- //}
+ if ((err = iphone_mux_pullbulk(cur_dev->phone)) < 0) {
+ if (verbose >= 1) fprintf(stderr, "%s: error %d when reading from device\n", __func__, err);
+ break;
+ }
}
if (verbose >= 0) fprintf(stderr, "%s: terminated\n", __func__);
@@ -495,7 +495,7 @@ static void *usbmuxd_client_init_thread(void *arg)
// iphone_error_t err;
iphone_device_t phone = NULL;
- struct device_use_info *cur_dev = NULL;
+ struct device_info *cur_dev = NULL;
if (!arg) {
if (verbose >= 1) fprintf(stderr, "%s: invalid client_data provided!\n", __func__);
@@ -608,13 +608,13 @@ connect:
phone = NULL;
cur_dev = NULL;
// first check if we already have an open connection
- if (device_use_list) {
+ if (devices) {
pthread_mutex_lock(&usbmux_mutex);
- for (i = 0; i < device_use_count; i++) {
- if (device_use_list[i]) {
- if (device_use_list[i]->device_id == c_req->device_id) {
- device_use_list[i]->use_count++;
- cur_dev = device_use_list[i];
+ for (i = 0; i < device_count; i++) {
+ if (devices[i]) {
+ if (devices[i]->device_id == c_req->device_id) {
+ devices[i]->use_count++;
+ cur_dev = devices[i];
phone = cur_dev->phone;
break;
}
@@ -635,10 +635,11 @@ connect:
}
pthread_mutex_unlock(&usb_mutex);
- // add to device list
+ // create device object
+ pthread_mutex_lock(&usbmux_mutex);
if (verbose >= 3) fprintf(stderr, "%s: add to device list\n", __func__);
- cur_dev = (struct device_use_info*)malloc(sizeof(struct device_use_info));
- memset(cur_dev, 0, sizeof(struct device_use_info));
+ cur_dev = (struct device_info*)malloc(sizeof(struct device_info));
+ memset(cur_dev, 0, sizeof(struct device_info));
cur_dev->use_count = 1;
cur_dev->device_id = c_req->device_id;
cur_dev->phone = phone;
@@ -646,13 +647,13 @@ connect:
pthread_mutex_init(&cur_dev->mutex, NULL);
pthread_mutex_init(&cur_dev->writer_mutex, NULL);
- if (verbose >= 3) fprintf(stderr, "%s: device_use_count = %d\n", __func__, device_use_count);
+ if (verbose >= 3) fprintf(stderr, "%s: device_count = %d\n", __func__, device_count);
- pthread_mutex_lock(&usbmux_mutex);
- device_use_list = (struct device_use_info**)realloc(device_use_list, sizeof(struct device_use_info*) * (device_use_count+1));
- if (device_use_list) {
- device_use_list[device_use_count] = cur_dev;
- device_use_count++;
+ // add to list of devices
+ devices = (struct device_info**)realloc(devices, sizeof(struct device_info*) * (device_count+1));
+ if (devices) {
+ devices[device_count] = cur_dev;
+ devices++;
}
pthread_mutex_unlock(&usbmux_mutex);
} else {
@@ -671,43 +672,22 @@ connect:
}
// start bulk reader thread (once per device)
+ pthread_mutex_lock(&cur_dev->mutex);
if (cur_dev->bulk_reader == 0) {
pthread_create(&cur_dev->bulk_reader, NULL, usbmuxd_bulk_reader_thread, cur_dev);
}
+ pthread_mutex_unlock(&cur_dev->mutex);
// start connection handler thread
cdata->handler_dead = 0;
cdata->tag = c_req->header.tag;
- cdata->duinfo = cur_dev;
+ cdata->dev = cur_dev;
if (pthread_create(&cdata->handler, NULL, usbmuxd_client_handler_thread, cdata) != 0) {
if (verbose >= 3) fprintf(stderr, "%s: could not create usbmuxd_client_handler_thread!\n", __func__);
cdata->handler = 0;
goto leave;
}
- //sent_result = 0;
-
- // TODO: wait for connect result?
- // if connect failed, don't run this loop:
-
- /*
- // start reading data from the connected device
- while (!quit_flag && !cdata->handler_dead) {
- iphone_mux_pullbulk(cur_dev->phone);
- err = iphone_mux_get_error(cdata->muxclient);
- if (err != IPHONE_E_SUCCESS) {
- break;
- }
- }
-
- if (!sent_result) {
- //fprintf(stderr, "Sending error message %d tag %d\n", err, c_req.header.tag);
- err = iphone_mux_get_error(cdata->muxclient);
- //usbmuxd_send_result(cdata->socket, c_req.header.tag, err);
- }*/
-
- //fprintf(stderr, "%s: terminating\n", __func__);
-
// wait for handler thread to finish its work
if (cdata->handler != 0) {
pthread_join(cdata->handler, NULL);
@@ -754,23 +734,23 @@ leave:
free(cur_dev);
cur_dev = NULL;
pthread_mutex_lock(&usbmux_mutex);
- if (device_use_count > 1) {
- struct device_use_info **newlist;
+ if (device_count > 1) {
+ struct device_info **newlist;
int j;
- newlist = (struct device_use_info**)malloc(sizeof(struct device_use_info*) * device_use_count-1);
- for (i = 0; i < device_use_count; i++) {
- if (device_use_list[i] != NULL) {
- newlist[j++] = device_use_list[i];
+ newlist = (struct device_info**)malloc(sizeof(struct device_info*) * device_count-1);
+ for (i = 0; i < device_count; i++) {
+ if (devices[i] != NULL) {
+ newlist[j++] = devices[i];
}
}
- free(device_use_list);
- device_use_list = newlist;
- device_use_count--;
+ free(devices);
+ devices = newlist;
+ device_count--;
} else {
- free(device_use_list);
- device_use_list = NULL;
- device_use_count = 0;
+ free(devices);
+ devices = NULL;
+ device_count = 0;
}
pthread_mutex_unlock(&usbmux_mutex);
}
@@ -1013,6 +993,8 @@ int main(int argc, char **argv)
chmod(USBMUXD_SOCKET_FILE, 0666);
+ if (verbose >= 3) iphone_set_debug(1);
+
if (!foreground) {
if (daemonize() < 0) {
fprintf(stderr, "usbmuxd: FATAL: Could not daemonize!\n");