summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/libiphone/libiphone.h4
-rw-r--r--src/AFC.c22
-rw-r--r--src/ifuse.c16
-rw-r--r--src/iphone.c14
-rw-r--r--src/lockdown.c164
-rw-r--r--src/lockdown.h16
-rw-r--r--src/main.c21
-rw-r--r--src/usbmux.c4
8 files changed, 137 insertions, 124 deletions
diff --git a/include/libiphone/libiphone.h b/include/libiphone/libiphone.h
index 26d35ab..249b9b3 100644
--- a/include/libiphone/libiphone.h
+++ b/include/libiphone/libiphone.h
@@ -42,9 +42,11 @@ extern "C" {
42#define IPHONE_E_INVALID_CONF -7 42#define IPHONE_E_INVALID_CONF -7
43#define IPHONE_E_PAIRING_FAILED -8 43#define IPHONE_E_PAIRING_FAILED -8
44#define IPHONE_E_SSL_ERROR -9 44#define IPHONE_E_SSL_ERROR -9
45#define IPHONE_E_PLIST_ERROR -10
46#define IPHONE_E_DICT_ERROR -11
45 47
46//afc specific error 48//afc specific error
47#define IPHONE_E_NO_SUCH_FILE -10 49#define IPHONE_E_NO_SUCH_FILE -12
48 50
49typedef short iphone_error_t; 51typedef short iphone_error_t;
50 52
diff --git a/src/AFC.c b/src/AFC.c
index 44dcee5..d2bae97 100644
--- a/src/AFC.c
+++ b/src/AFC.c
@@ -159,7 +159,7 @@ static int dispatch_AFC_packet(iphone_afc_client_t client, const char *data, int
159 return -1; 159 return -1;
160 } 160 }
161 memcpy(buffer+sizeof(AFCPacket), data, offset); 161 memcpy(buffer+sizeof(AFCPacket), data, offset);
162 bytes = iphone_mux_send(client->connection, buffer, client->afc_packet->this_length); 162 iphone_mux_send(client->connection, buffer, client->afc_packet->this_length, &bytes);
163 free(buffer); 163 free(buffer);
164 if (bytes <= 0) { 164 if (bytes <= 0) {
165 return bytes; 165 return bytes;
@@ -172,7 +172,7 @@ static int dispatch_AFC_packet(iphone_afc_client_t client, const char *data, int
172 fwrite(data+offset, 1, length-offset, stdout); 172 fwrite(data+offset, 1, length-offset, stdout);
173 } 173 }
174 174
175 bytes = iphone_mux_send(client->connection, data+offset, length-offset); 175 iphone_mux_send(client->connection, data+offset, length-offset, &bytes);
176 return bytes; 176 return bytes;
177 } else { 177 } else {
178 if (debug) fprintf(stderr, "dispatch_AFC_packet doin things the old way\n"); 178 if (debug) fprintf(stderr, "dispatch_AFC_packet doin things the old way\n");
@@ -183,7 +183,7 @@ static int dispatch_AFC_packet(iphone_afc_client_t client, const char *data, int
183 if (length > 0) { memcpy(buffer+sizeof(AFCPacket), data, length); buffer[sizeof(AFCPacket)+length] = '\0'; } 183 if (length > 0) { memcpy(buffer+sizeof(AFCPacket), data, length); buffer[sizeof(AFCPacket)+length] = '\0'; }
184 if (debug) fwrite(buffer, 1, client->afc_packet->this_length, stdout); 184 if (debug) fwrite(buffer, 1, client->afc_packet->this_length, stdout);
185 if (debug) fprintf(stderr, "\n"); 185 if (debug) fprintf(stderr, "\n");
186 bytes = iphone_mux_send(client->connection, buffer, client->afc_packet->this_length); 186 iphone_mux_send(client->connection, buffer, client->afc_packet->this_length, &bytes);
187 187
188 if (buffer) { 188 if (buffer) {
189 free(buffer); 189 free(buffer);
@@ -212,7 +212,7 @@ static int receive_AFC_data(iphone_afc_client_t client, char **dump_here) {
212 int bytes = 0, recv_len = 0, current_count=0; 212 int bytes = 0, recv_len = 0, current_count=0;
213 int retval = 0; 213 int retval = 0;
214 214
215 bytes = iphone_mux_recv(client->connection, buffer, sizeof(AFCPacket) * 4); 215 iphone_mux_recv(client->connection, buffer, sizeof(AFCPacket) * 4, &bytes);
216 if (bytes <= 0) { 216 if (bytes <= 0) {
217 free(buffer); 217 free(buffer);
218 fprintf(stderr, "Just didn't get enough.\n"); 218 fprintf(stderr, "Just didn't get enough.\n");
@@ -265,7 +265,7 @@ static int receive_AFC_data(iphone_afc_client_t client, char **dump_here) {
265 buffer = (char*)malloc(sizeof(char) * (recv_len < MAXIMUM_PACKET_SIZE) ? recv_len : MAXIMUM_PACKET_SIZE); 265 buffer = (char*)malloc(sizeof(char) * (recv_len < MAXIMUM_PACKET_SIZE) ? recv_len : MAXIMUM_PACKET_SIZE);
266 final_buffer = (char*)malloc(sizeof(char) * recv_len); 266 final_buffer = (char*)malloc(sizeof(char) * recv_len);
267 while(current_count < recv_len){ 267 while(current_count < recv_len){
268 bytes = iphone_mux_recv(client->connection, buffer, recv_len-current_count); 268 iphone_mux_recv(client->connection, buffer, recv_len-current_count, &bytes);
269 if (debug) fprintf(stderr, "receive_AFC_data: still collecting packets\n"); 269 if (debug) fprintf(stderr, "receive_AFC_data: still collecting packets\n");
270 if (bytes < 0) 270 if (bytes < 0)
271 { 271 {
@@ -331,7 +331,7 @@ iphone_error_t iphone_afc_get_dir_list ( iphone_afc_client_t client, const char
331 char *data = NULL, **list_loc = NULL; 331 char *data = NULL, **list_loc = NULL;
332 iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR; 332 iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR;
333 333
334 if (!client || !dir || !list) return IPHONE_E_INVALID_ARG; 334 if (!client || !dir || !list || (list && *list)) return IPHONE_E_INVALID_ARG;
335 335
336 afc_lock(client); 336 afc_lock(client);
337 337
@@ -714,11 +714,11 @@ iphone_error_t iphone_afc_read_file ( iphone_afc_client_t client, iphone_afc_fil
714 // Receive the data 714 // Receive the data
715 bytes_loc = receive_AFC_data(client, &input); 715 bytes_loc = receive_AFC_data(client, &input);
716 if (debug) fprintf(stderr, "afc_read_file: bytes returned: %i\n", bytes_loc); 716 if (debug) fprintf(stderr, "afc_read_file: bytes returned: %i\n", bytes_loc);
717 if (bytes < 0) { 717 if (bytes_loc < 0) {
718 if (input) free(input); 718 if (input) free(input);
719 afc_unlock(client); 719 afc_unlock(client);
720 return IPHONE_E_NOT_ENOUGH_DATA; 720 return IPHONE_E_NOT_ENOUGH_DATA;
721 } else if (bytes == 0) { 721 } else if (bytes_loc == 0) {
722 if (input) free(input); 722 if (input) free(input);
723 afc_unlock(client); 723 afc_unlock(client);
724 *bytes = current_count; 724 *bytes = current_count;
@@ -756,7 +756,7 @@ iphone_error_t iphone_afc_write_file ( iphone_afc_client_t client, iphone_afc_fi
756 uint32 zero = 0, bytes_loc = 0, segments = (length / MAXIMUM_WRITE_SIZE), current_count = 0, i = 0; 756 uint32 zero = 0, bytes_loc = 0, segments = (length / MAXIMUM_WRITE_SIZE), current_count = 0, i = 0;
757 char *out_buffer = NULL; 757 char *out_buffer = NULL;
758 758
759 if (!client ||!client->afc_packet || !client->connection || !file || !bytes_loc) return IPHONE_E_INVALID_ARG; 759 if (!client ||!client->afc_packet || !client->connection || !file || !bytes) return IPHONE_E_INVALID_ARG;
760 760
761 afc_lock(client); 761 afc_lock(client);
762 762
@@ -821,8 +821,8 @@ iphone_error_t iphone_afc_write_file ( iphone_afc_client_t client, iphone_afc_fi
821 if (bytes_loc < 0) { 821 if (bytes_loc < 0) {
822 if (debug) fprintf(stderr, "afc_write_file: uh oh?\n"); 822 if (debug) fprintf(stderr, "afc_write_file: uh oh?\n");
823 } 823 }
824 824 *bytes = current_count;
825 return IPHONE_E_UNKNOWN_ERROR; 825 return IPHONE_E_SUCCESS;
826} 826}
827 827
828/** Closes a file on the phone. 828/** Closes a file on the phone.
diff --git a/src/ifuse.c b/src/ifuse.c
index f768423..6d2bae0 100644
--- a/src/ifuse.c
+++ b/src/ifuse.c
@@ -57,7 +57,7 @@ static int ifuse_readdir(const char *path, void *buf, fuse_fill_dir_t filler,
57 char **dirs; 57 char **dirs;
58 iphone_afc_client_t afc = fuse_get_context()->private_data; 58 iphone_afc_client_t afc = fuse_get_context()->private_data;
59 59
60 dirs = iphone_afc_get_dir_list(afc, path); 60 iphone_afc_get_dir_list(afc, path, &dirs);
61 61
62 if(!dirs) 62 if(!dirs)
63 return -ENOENT; 63 return -ENOENT;
@@ -119,8 +119,8 @@ static int ifuse_read(const char *path, char *buf, size_t size, off_t offset,
119 return -ENOENT; 119 return -ENOENT;
120 } 120 }
121 121
122 bytes = iphone_afc_seek_file(afc, file, offset); 122 if (IPHONE_E_SUCCESS == iphone_afc_seek_file(afc, file, offset))
123 bytes = iphone_afc_read_file(afc, file, buf, size); 123 iphone_afc_read_file(afc, file, buf, size, &bytes);
124 return bytes; 124 return bytes;
125} 125}
126 126
@@ -134,8 +134,8 @@ static int ifuse_write(const char *path, const char *buf, size_t size, off_t off
134 file = g_hash_table_lookup(file_handles, &(fi->fh)); 134 file = g_hash_table_lookup(file_handles, &(fi->fh));
135 if (!file) return -ENOENT; 135 if (!file) return -ENOENT;
136 136
137 bytes = iphone_afc_seek_file(afc, file, offset); 137 if (IPHONE_E_SUCCESS == iphone_afc_seek_file(afc, file, offset))
138 bytes = iphone_afc_write_file(afc, file, buf, size); 138 iphone_afc_write_file(afc, file, buf, size, &bytes);
139 return bytes; 139 return bytes;
140} 140}
141 141
@@ -179,8 +179,7 @@ void *ifuse_init(struct fuse_conn_info *conn) {
179 return NULL; 179 return NULL;
180 } 180 }
181 181
182 port = iphone_lckd_start_service(control, "com.apple.afc"); 182 if (IPHONE_E_SUCCESS == iphone_lckd_start_service(control, "com.apple.afc", &port) && !port) {
183 if (!port) {
184 iphone_lckd_free_client(control); 183 iphone_lckd_free_client(control);
185 iphone_free_device(phone); 184 iphone_free_device(phone);
186 fprintf(stderr, "Something went wrong when starting AFC."); 185 fprintf(stderr, "Something went wrong when starting AFC.");
@@ -206,9 +205,10 @@ int ifuse_flush(const char *path, struct fuse_file_info *fi) {
206 205
207int ifuse_statfs(const char *path, struct statvfs *stats) { 206int ifuse_statfs(const char *path, struct statvfs *stats) {
208 iphone_afc_client_t afc = fuse_get_context()->private_data; 207 iphone_afc_client_t afc = fuse_get_context()->private_data;
209 char **info_raw = iphone_afc_get_devinfo(afc); 208 char **info_raw = NULL;
210 uint32_t totalspace = 0, freespace = 0, blocksize = 0, i = 0; 209 uint32_t totalspace = 0, freespace = 0, blocksize = 0, i = 0;
211 210
211 iphone_afc_get_devinfo(afc, &info_raw);
212 if (!info_raw) return -ENOENT; 212 if (!info_raw) return -ENOENT;
213 213
214 for (i = 0; info_raw[i]; i++) { 214 for (i = 0; info_raw[i]; i++) {
diff --git a/src/iphone.c b/src/iphone.c
index f5bc206..68963fe 100644
--- a/src/iphone.c
+++ b/src/iphone.c
@@ -140,14 +140,14 @@ iphone_error_t iphone_free_device ( iphone_device_t device ) {
140 140
141 if (device->buffer) { 141 if (device->buffer) {
142 free(device->buffer); 142 free(device->buffer);
143 if (device->device) {
144 usb_release_interface(device->device, 1);
145 usb_reset(device->device);
146 usb_close(device->device);
147 ret = IPHONE_E_SUCCESS;
148 }
149 free(device);
150 } 143 }
144 if (device->device) {
145 usb_release_interface(device->device, 1);
146 usb_reset(device->device);
147 usb_close(device->device);
148 ret = IPHONE_E_SUCCESS;
149 }
150 free(device);
151 return ret; 151 return ret;
152} 152}
153 153
diff --git a/src/lockdown.c b/src/lockdown.c
index a22b896..e5420a3 100644
--- a/src/lockdown.c
+++ b/src/lockdown.c
@@ -117,7 +117,7 @@ iphone_error_t iphone_lckd_free_client( iphone_lckd_client_t client ) {
117 * @return The number of bytes received 117 * @return The number of bytes received
118 */ 118 */
119iphone_error_t iphone_lckd_recv ( iphone_lckd_client_t client, char **dump_data, uint32_t *recv_bytes ) { 119iphone_error_t iphone_lckd_recv ( iphone_lckd_client_t client, char **dump_data, uint32_t *recv_bytes ) {
120 if (!client || dump_data || !recv_bytes) return IPHONE_E_INVALID_ARG; 120 if (!client || !dump_data || !recv_bytes) return IPHONE_E_INVALID_ARG;
121 iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR; 121 iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR;
122 char *receive; 122 char *receive;
123 uint32 datalen = 0, bytes = 0; 123 uint32 datalen = 0, bytes = 0;
@@ -188,12 +188,13 @@ iphone_error_t iphone_lckd_send ( iphone_lckd_client_t client, char *raw_data, u
188 * 188 *
189 * @return 1 on success and 0 on failure. 189 * @return 1 on success and 0 on failure.
190 */ 190 */
191int lockdownd_hello(iphone_lckd_client_t control) { 191iphone_error_t lockdownd_hello(iphone_lckd_client_t control) {
192 if (!control) return 0; 192 if (!control) return IPHONE_E_INVALID_ARG;
193 xmlDocPtr plist = new_plist(); 193 xmlDocPtr plist = new_plist();
194 xmlNode *dict, *key; 194 xmlNode *dict, *key;
195 char **dictionary; 195 char **dictionary;
196 int bytes = 0, i = 0; 196 int bytes = 0, i = 0;
197 iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR;
197 198
198 if (debug) printf("lockdownd_hello() called\n"); 199 if (debug) printf("lockdownd_hello() called\n");
199 dict = add_child_to_plist(plist, "dict", "\n", NULL, 0); 200 dict = add_child_to_plist(plist, "dict", "\n", NULL, 0);
@@ -202,33 +203,33 @@ int lockdownd_hello(iphone_lckd_client_t control) {
202 uint32 length; 203 uint32 length;
203 204
204 xmlDocDumpMemory(plist, (xmlChar **)&XML_content, &length); 205 xmlDocDumpMemory(plist, (xmlChar **)&XML_content, &length);
205 bytes = iphone_lckd_send(control, XML_content, length); 206 ret = iphone_lckd_send(control, XML_content, length, &bytes);
206 207
207 xmlFree(XML_content); 208 xmlFree(XML_content);
208 xmlFreeDoc(plist); plist = NULL; 209 xmlFreeDoc(plist); plist = NULL;
209 bytes = iphone_lckd_recv(control, &XML_content); 210 ret = iphone_lckd_recv(control, &XML_content, &bytes);
210 211
211 plist = xmlReadMemory(XML_content, bytes, NULL, NULL, 0); 212 plist = xmlReadMemory(XML_content, bytes, NULL, NULL, 0);
212 if (!plist) return 0; 213 if (!plist) return IPHONE_E_PLIST_ERROR;
213 dict = xmlDocGetRootElement(plist); 214 dict = xmlDocGetRootElement(plist);
214 for (dict = dict->children; dict; dict = dict->next) { 215 for (dict = dict->children; dict; dict = dict->next) {
215 if (!xmlStrcmp(dict->name, "dict")) break; 216 if (!xmlStrcmp(dict->name, "dict")) break;
216 } 217 }
217 if (!dict) return 0; 218 if (!dict) return IPHONE_E_DICT_ERROR;
218 dictionary = read_dict_element_strings(dict); 219 dictionary = read_dict_element_strings(dict);
219 xmlFreeDoc(plist); 220 xmlFreeDoc(plist);
220 free(XML_content); 221 free(XML_content);
221 222
222 for (i = 0; dictionary[i]; i+=2) { 223 for (i = 0; dictionary[i]; i+=2) {
223 if (!strcmp(dictionary[i], "Result") && !strcmp(dictionary[i+1], "Success")) { 224 if (!strcmp(dictionary[i], "Result") && !strcmp(dictionary[i+1], "Success")) {
224 free_dictionary(dictionary);
225 if (debug) printf("lockdownd_hello(): success\n"); 225 if (debug) printf("lockdownd_hello(): success\n");
226 return 1; 226 ret = IPHONE_E_SUCCESS;
227 break;
227 } 228 }
228 } 229 }
229 230
230 free_dictionary(dictionary); 231 free_dictionary(dictionary);
231 return 0; 232 return ret;
232} 233}
233 234
234/** Generic function to handle simple (key, value) requests. 235/** Generic function to handle simple (key, value) requests.
@@ -237,10 +238,11 @@ int lockdownd_hello(iphone_lckd_client_t control) {
237 * @param key the key to request 238 * @param key the key to request
238 * @param value a pointer to the requested value 239 * @param value a pointer to the requested value
239 * 240 *
240 * @return 1 on success and 0 on failure. 241 * @return IPHONE_E_SUCCESS on success.
241 */ 242 */
242int lockdownd_generic_get_value(iphone_lckd_client_t control, char *req_key, char **value) 243iphone_error_t lockdownd_generic_get_value(iphone_lckd_client_t control, char *req_key, char **value)
243{ 244{
245 if (!control || !req_key || !value || (value && *value)) return IPHONE_E_INVALID_ARG;
244 xmlDocPtr plist = new_plist(); 246 xmlDocPtr plist = new_plist();
245 xmlNode *dict = NULL; 247 xmlNode *dict = NULL;
246 xmlNode *key = NULL;; 248 xmlNode *key = NULL;;
@@ -248,6 +250,7 @@ int lockdownd_generic_get_value(iphone_lckd_client_t control, char *req_key, cha
248 int bytes = 0, i = 0; 250 int bytes = 0, i = 0;
249 char *XML_content = NULL; 251 char *XML_content = NULL;
250 uint32 length = 0; 252 uint32 length = 0;
253 iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR;
251 254
252 /* Setup DevicePublicKey request plist */ 255 /* Setup DevicePublicKey request plist */
253 dict = add_child_to_plist(plist, "dict", "\n", NULL, 0); 256 dict = add_child_to_plist(plist, "dict", "\n", NULL, 0);
@@ -256,21 +259,25 @@ int lockdownd_generic_get_value(iphone_lckd_client_t control, char *req_key, cha
256 xmlDocDumpMemory(plist, (xmlChar**)&XML_content, &length); 259 xmlDocDumpMemory(plist, (xmlChar**)&XML_content, &length);
257 260
258 /* send to iPhone */ 261 /* send to iPhone */
259 bytes = iphone_lckd_send(control, XML_content, length); 262 ret = iphone_lckd_send(control, XML_content, length, &bytes);
260 263
261 xmlFree(XML_content); 264 xmlFree(XML_content);
262 xmlFreeDoc(plist); plist = NULL; 265 xmlFreeDoc(plist); plist = NULL;
263 266
267 if (ret != IPHONE_E_SUCCESS) return ret;
268
264 /* Now get iPhone's answer */ 269 /* Now get iPhone's answer */
265 bytes = iphone_lckd_recv(control, &XML_content); 270 ret = iphone_lckd_recv(control, &XML_content, &bytes);
271
272 if (ret != IPHONE_E_SUCCESS) return ret;
266 273
267 plist = xmlReadMemory(XML_content, bytes, NULL, NULL, 0); 274 plist = xmlReadMemory(XML_content, bytes, NULL, NULL, 0);
268 if (!plist) return 0; 275 if (!plist) return IPHONE_E_PLIST_ERROR;
269 dict = xmlDocGetRootElement(plist); 276 dict = xmlDocGetRootElement(plist);
270 for (dict = dict->children; dict; dict = dict->next) { 277 for (dict = dict->children; dict; dict = dict->next) {
271 if (!xmlStrcmp(dict->name, "dict")) break; 278 if (!xmlStrcmp(dict->name, "dict")) break;
272 } 279 }
273 if (!dict) return 0; 280 if (!dict) return IPHONE_E_DICT_ERROR;
274 281
275 /* Parse xml to check success and to find public key */ 282 /* Parse xml to check success and to find public key */
276 dictionary = read_dict_element_strings(dict); 283 dictionary = read_dict_element_strings(dict);
@@ -291,7 +298,8 @@ int lockdownd_generic_get_value(iphone_lckd_client_t control, char *req_key, cha
291 free_dictionary(dictionary); 298 free_dictionary(dictionary);
292 dictionary = NULL; 299 dictionary = NULL;
293 } 300 }
294 return success; 301 if (success) ret = IPHONE_E_SUCCESS;
302 return ret;
295} 303}
296 304
297/** Askes for the device's unique id. Part of the lockdownd handshake. 305/** Askes for the device's unique id. Part of the lockdownd handshake.
@@ -300,7 +308,7 @@ int lockdownd_generic_get_value(iphone_lckd_client_t control, char *req_key, cha
300 * 308 *
301 * @return 1 on success and 0 on failure. 309 * @return 1 on success and 0 on failure.
302 */ 310 */
303int lockdownd_get_device_uid(iphone_lckd_client_t control, char **uid) 311iphone_error_t lockdownd_get_device_uid(iphone_lckd_client_t control, char **uid)
304{ 312{
305 return lockdownd_generic_get_value(control, "UniqueDeviceID", uid); 313 return lockdownd_generic_get_value(control, "UniqueDeviceID", uid);
306} 314}
@@ -311,7 +319,7 @@ int lockdownd_get_device_uid(iphone_lckd_client_t control, char **uid)
311 * 319 *
312 * @return 1 on success and 0 on failure. 320 * @return 1 on success and 0 on failure.
313 */ 321 */
314int lockdownd_get_device_public_key(iphone_lckd_client_t control, char **public_key) 322iphone_error_t lockdownd_get_device_public_key(iphone_lckd_client_t control, char **public_key)
315{ 323{
316 return lockdownd_generic_get_value(control, "DevicePublicKey", public_key); 324 return lockdownd_generic_get_value(control, "DevicePublicKey", public_key);
317} 325}
@@ -331,16 +339,16 @@ iphone_error_t iphone_lckd_new_client ( iphone_device_t device, iphone_lckd_clie
331 char *host_id = NULL; 339 char *host_id = NULL;
332 340
333 iphone_lckd_client_t client_loc = new_lockdownd_client( device ); 341 iphone_lckd_client_t client_loc = new_lockdownd_client( device );
334 if (!lockdownd_hello(client_loc)){ 342 if (IPHONE_E_SUCCESS != lockdownd_hello(client_loc)){
335 fprintf(stderr, "Hello failed in the lockdownd client.\n"); 343 fprintf(stderr, "Hello failed in the lockdownd client.\n");
336 ret = IPHONE_E_NOT_ENOUGH_DATA; 344 ret = IPHONE_E_NOT_ENOUGH_DATA;
337 } 345 }
338 346
339 347
340 char *uid = NULL; 348 char *uid = NULL;
341 if(IPHONE_E_SUCCESS == ret && !lockdownd_get_device_uid(client_loc, &uid)){ 349 ret = lockdownd_get_device_uid(client_loc, &uid);
350 if(IPHONE_E_SUCCESS != ret){
342 fprintf(stderr, "Device refused to send uid.\n"); 351 fprintf(stderr, "Device refused to send uid.\n");
343 ret = IPHONE_E_NOT_ENOUGH_DATA;
344 } 352 }
345 353
346 host_id = get_host_id(); 354 host_id = get_host_id();
@@ -357,9 +365,8 @@ iphone_error_t iphone_lckd_new_client ( iphone_device_t device, iphone_lckd_clie
357 uid = NULL; 365 uid = NULL;
358 } 366 }
359 367
360 if (IPHONE_E_SUCCESS == ret && lockdownd_start_SSL_session(client_loc, host_id)) { 368 ret = lockdownd_start_SSL_session(client_loc, host_id);
361 ret = IPHONE_E_SUCCESS; 369 if (IPHONE_E_SUCCESS != ret ) {
362 } else {
363 ret = IPHONE_E_SSL_ERROR; 370 ret = IPHONE_E_SSL_ERROR;
364 fprintf(stderr, "SSL Session opening failed.\n"); 371 fprintf(stderr, "SSL Session opening failed.\n");
365 } 372 }
@@ -381,9 +388,9 @@ iphone_error_t iphone_lckd_new_client ( iphone_device_t device, iphone_lckd_clie
381 * 388 *
382 * @return 1 on success and 0 on failure 389 * @return 1 on success and 0 on failure
383 */ 390 */
384int lockdownd_pair_device(iphone_lckd_client_t control, char *uid, char *host_id) 391iphone_error_t lockdownd_pair_device(iphone_lckd_client_t control, char *uid, char *host_id)
385{ 392{
386 int ret = 0; 393 iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR;
387 xmlDocPtr plist = new_plist(); 394 xmlDocPtr plist = new_plist();
388 xmlNode *dict = NULL; 395 xmlNode *dict = NULL;
389 xmlNode *dictRecord = NULL; 396 xmlNode *dictRecord = NULL;
@@ -397,15 +404,16 @@ int lockdownd_pair_device(iphone_lckd_client_t control, char *uid, char *host_id
397 char* root_cert_b64 = NULL; 404 char* root_cert_b64 = NULL;
398 char *public_key_b64 = NULL; 405 char *public_key_b64 = NULL;
399 406
400 if(!lockdownd_get_device_public_key(control, &public_key_b64)){ 407 ret = lockdownd_get_device_public_key(control, &public_key_b64);
408 if(ret != IPHONE_E_SUCCESS){
401 fprintf(stderr, "Device refused to send public key.\n"); 409 fprintf(stderr, "Device refused to send public key.\n");
402 return 0; 410 return ret;
403 } 411 }
404 412
405 413 ret = lockdownd_gen_pair_cert(public_key_b64, &device_cert_b64, &host_cert_b64, &root_cert_b64);
406 if(!lockdownd_gen_pair_cert(public_key_b64, &device_cert_b64, &host_cert_b64, &root_cert_b64)){ 414 if(ret != IPHONE_E_SUCCESS){
407 free(public_key_b64); 415 free(public_key_b64);
408 return 0; 416 return ret;
409 } 417 }
410 418
411 /* Setup Pair request plist */ 419 /* Setup Pair request plist */
@@ -423,13 +431,17 @@ int lockdownd_pair_device(iphone_lckd_client_t control, char *uid, char *host_id
423 printf("XML Pairing request : %s\n",XML_content); 431 printf("XML Pairing request : %s\n",XML_content);
424 432
425 /* send to iPhone */ 433 /* send to iPhone */
426 bytes = iphone_lckd_send(control, XML_content, length); 434 ret = iphone_lckd_send(control, XML_content, length, &bytes);
427 435
428 xmlFree(XML_content); 436 xmlFree(XML_content);
429 xmlFreeDoc(plist); plist = NULL; 437 xmlFreeDoc(plist); plist = NULL;
430 438
439 if (ret != IPHONE_E_SUCCESS) return ret;
440
431 /* Now get iPhone's answer */ 441 /* Now get iPhone's answer */
432 bytes = iphone_lckd_recv(control, &XML_content); 442 ret = iphone_lckd_recv(control, &XML_content, &bytes);
443
444 if (ret != IPHONE_E_SUCCESS) return ret;
433 445
434 if (debug) { 446 if (debug) {
435 printf("lockdown_pair_device: iPhone's response to our pair request:\n"); 447 printf("lockdown_pair_device: iPhone's response to our pair request:\n");
@@ -440,7 +452,7 @@ int lockdownd_pair_device(iphone_lckd_client_t control, char *uid, char *host_id
440 plist = xmlReadMemory(XML_content, bytes, NULL, NULL, 0); 452 plist = xmlReadMemory(XML_content, bytes, NULL, NULL, 0);
441 if (!plist) { 453 if (!plist) {
442 free(public_key_b64); 454 free(public_key_b64);
443 return 0; 455 return IPHONE_E_PLIST_ERROR;
444 } 456 }
445 dict = xmlDocGetRootElement(plist); 457 dict = xmlDocGetRootElement(plist);
446 for (dict = dict->children; dict; dict = dict->next) { 458 for (dict = dict->children; dict; dict = dict->next) {
@@ -448,7 +460,7 @@ int lockdownd_pair_device(iphone_lckd_client_t control, char *uid, char *host_id
448 } 460 }
449 if (!dict) { 461 if (!dict) {
450 free(public_key_b64); 462 free(public_key_b64);
451 return 0; 463 return IPHONE_E_DICT_ERROR;
452 } 464 }
453 465
454 /* Parse xml to check success and to find public key */ 466 /* Parse xml to check success and to find public key */
@@ -472,9 +484,10 @@ int lockdownd_pair_device(iphone_lckd_client_t control, char *uid, char *host_id
472 if (success) { 484 if (success) {
473 if (debug) printf("lockdownd_pair_device: pair success\n"); 485 if (debug) printf("lockdownd_pair_device: pair success\n");
474 store_device_public_key(uid, public_key_b64); 486 store_device_public_key(uid, public_key_b64);
475 ret = 1; 487 ret = IPHONE_E_SUCCESS;
476 } else { 488 } else {
477 if (debug) printf("lockdownd_pair_device: pair failure\n"); 489 if (debug) printf("lockdownd_pair_device: pair failure\n");
490 ret = IPHONE_E_PAIRING_FAILED;
478 } 491 }
479 free(public_key_b64); 492 free(public_key_b64);
480 return ret; 493 return ret;
@@ -483,11 +496,12 @@ int lockdownd_pair_device(iphone_lckd_client_t control, char *uid, char *host_id
483/** Generates the device certificate from the public key as well as the host 496/** Generates the device certificate from the public key as well as the host
484 * and root certificates. 497 * and root certificates.
485 * 498 *
486 * @return 1 on success and 0 on failure. 499 * @return IPHONE_E_SUCCESS on success.
487 */ 500 */
488int lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char **host_cert_b64, char **root_cert_b64) 501iphone_error_t lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char **host_cert_b64, char **root_cert_b64)
489{ 502{
490 int ret = 0, error = 0; 503 if (!public_key_b64 || !device_cert_b64 || !host_cert_b64 || !root_cert_b64) return IPHONE_E_INVALID_ARG;
504 iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR;
491 505
492 gnutls_datum_t modulus = {NULL, 0}; 506 gnutls_datum_t modulus = {NULL, 0};
493 gnutls_datum_t exponent = {NULL, 0}; 507 gnutls_datum_t exponent = {NULL, 0};
@@ -501,7 +515,6 @@ int lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char *
501 /* now decode the PEM encoded key */ 515 /* now decode the PEM encoded key */
502 gnutls_datum_t der_pub_key; 516 gnutls_datum_t der_pub_key;
503 if( GNUTLS_E_SUCCESS == gnutls_pem_base64_decode_alloc ("RSA PUBLIC KEY", &pem_pub_key, &der_pub_key) ){ 517 if( GNUTLS_E_SUCCESS == gnutls_pem_base64_decode_alloc ("RSA PUBLIC KEY", &pem_pub_key, &der_pub_key) ){
504 ret = 1;
505 518
506 /* initalize asn.1 parser */ 519 /* initalize asn.1 parser */
507 ASN1_TYPE pkcs1 = ASN1_TYPE_EMPTY; 520 ASN1_TYPE pkcs1 = ASN1_TYPE_EMPTY;
@@ -522,7 +535,7 @@ int lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char *
522 ret1 = asn1_read_value (asn1_pub_key, "modulus", modulus.data, &modulus.size); 535 ret1 = asn1_read_value (asn1_pub_key, "modulus", modulus.data, &modulus.size);
523 ret2 = asn1_read_value (asn1_pub_key, "publicExponent", exponent.data, &exponent.size); 536 ret2 = asn1_read_value (asn1_pub_key, "publicExponent", exponent.data, &exponent.size);
524 if (ASN1_SUCCESS == ret1 && ASN1_SUCCESS == ret2) 537 if (ASN1_SUCCESS == ret1 && ASN1_SUCCESS == ret2)
525 ret = 1; 538 ret = IPHONE_E_SUCCESS;
526 } 539 }
527 if (asn1_pub_key) 540 if (asn1_pub_key)
528 asn1_delete_structure(&asn1_pub_key); 541 asn1_delete_structure(&asn1_pub_key);
@@ -532,7 +545,7 @@ int lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char *
532 } 545 }
533 546
534 /* now generate certifcates */ 547 /* now generate certifcates */
535 if (1 == ret && 0 != modulus.size && 0 != exponent.size) { 548 if (IPHONE_E_SUCCESS == ret && 0 != modulus.size && 0 != exponent.size) {
536 549
537 gnutls_global_init(); 550 gnutls_global_init();
538 gnutls_datum_t essentially_null = {strdup("abababababababab"), strlen("abababababababab")}; 551 gnutls_datum_t essentially_null = {strdup("abababababababab"), strlen("abababababababab")};
@@ -552,20 +565,20 @@ int lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char *
552 /* get root cert */ 565 /* get root cert */
553 gnutls_datum_t pem_root_cert = {NULL, 0}; 566 gnutls_datum_t pem_root_cert = {NULL, 0};
554 get_root_certificate(&pem_root_cert); 567 get_root_certificate(&pem_root_cert);
555 ret = gnutls_x509_crt_import(root_cert, &pem_root_cert, GNUTLS_X509_FMT_PEM); 568 if (GNUTLS_E_SUCCESS != gnutls_x509_crt_import(root_cert, &pem_root_cert, GNUTLS_X509_FMT_PEM))
556 if (ret != GNUTLS_E_SUCCESS) error = 1; 569 ret = IPHONE_E_SSL_ERROR;
557 570
558 /* get host cert */ 571 /* get host cert */
559 gnutls_datum_t pem_host_cert = {NULL, 0}; 572 gnutls_datum_t pem_host_cert = {NULL, 0};
560 get_host_certificate(&pem_host_cert); 573 get_host_certificate(&pem_host_cert);
561 ret = gnutls_x509_crt_import(host_cert, &pem_host_cert, GNUTLS_X509_FMT_PEM); 574 if (GNUTLS_E_SUCCESS != gnutls_x509_crt_import(host_cert, &pem_host_cert, GNUTLS_X509_FMT_PEM))
562 if (ret != GNUTLS_E_SUCCESS) error = 1; 575 ret = IPHONE_E_SSL_ERROR;
563 576
564 /* get root private key */ 577 /* get root private key */
565 gnutls_datum_t pem_root_priv = {NULL, 0}; 578 gnutls_datum_t pem_root_priv = {NULL, 0};
566 get_root_private_key(&pem_root_priv); 579 get_root_private_key(&pem_root_priv);
567 ret = gnutls_x509_privkey_import(root_privkey, &pem_root_priv, GNUTLS_X509_FMT_PEM); 580 if (GNUTLS_E_SUCCESS != gnutls_x509_privkey_import(root_privkey, &pem_root_priv, GNUTLS_X509_FMT_PEM))
568 if (ret != GNUTLS_E_SUCCESS) error = 1; 581 ret = IPHONE_E_SSL_ERROR;
569 582
570 /* generate device certificate */ 583 /* generate device certificate */
571 gnutls_x509_crt_set_key(dev_cert, fake_privkey); 584 gnutls_x509_crt_set_key(dev_cert, fake_privkey);
@@ -576,7 +589,7 @@ int lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char *
576 gnutls_x509_crt_set_expiration_time(dev_cert, time(NULL) + (60 * 60 * 24 * 365 * 10)); 589 gnutls_x509_crt_set_expiration_time(dev_cert, time(NULL) + (60 * 60 * 24 * 365 * 10));
577 gnutls_x509_crt_sign(dev_cert, root_cert, root_privkey); 590 gnutls_x509_crt_sign(dev_cert, root_cert, root_privkey);
578 591
579 if (!error) { 592 if (IPHONE_E_SUCCESS == ret) {
580 /* if everything went well, export in PEM format */ 593 /* if everything went well, export in PEM format */
581 gnutls_datum_t dev_pem = {NULL, 0}; 594 gnutls_datum_t dev_pem = {NULL, 0};
582 gnutls_x509_crt_export(dev_cert, GNUTLS_X509_FMT_PEM, NULL, &dev_pem.size); 595 gnutls_x509_crt_export(dev_cert, GNUTLS_X509_FMT_PEM, NULL, &dev_pem.size);
@@ -587,7 +600,6 @@ int lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char *
587 *device_cert_b64 = g_base64_encode(dev_pem.data, dev_pem.size); 600 *device_cert_b64 = g_base64_encode(dev_pem.data, dev_pem.size);
588 *host_cert_b64 = g_base64_encode(pem_host_cert.data, pem_host_cert.size); 601 *host_cert_b64 = g_base64_encode(pem_host_cert.data, pem_host_cert.size);
589 *root_cert_b64 = g_base64_encode(pem_root_cert.data, pem_root_cert.size); 602 *root_cert_b64 = g_base64_encode(pem_root_cert.data, pem_root_cert.size);
590 ret = 1;
591 } 603 }
592 gnutls_free(pem_root_priv.data); 604 gnutls_free(pem_root_priv.data);
593 gnutls_free(pem_root_cert.data); 605 gnutls_free(pem_root_cert.data);
@@ -600,12 +612,8 @@ int lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char *
600 612
601 gnutls_free(der_pub_key.data); 613 gnutls_free(der_pub_key.data);
602 g_free(pem_pub_key.data); 614 g_free(pem_pub_key.data);
603 615
604 if (error) { 616 return ret;
605 return 0;
606 } else {
607 return ret;
608 }
609} 617}
610 618
611/** Starts SSL communication with lockdownd after the iPhone has been paired. 619/** Starts SSL communication with lockdownd after the iPhone has been paired.
@@ -615,37 +623,41 @@ int lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char *
615 * 623 *
616 * @return 1 on success and 0 on failure 624 * @return 1 on success and 0 on failure
617 */ 625 */
618int lockdownd_start_SSL_session(iphone_lckd_client_t control, const char *HostID) { 626iphone_error_t lockdownd_start_SSL_session(iphone_lckd_client_t control, const char *HostID) {
619 xmlDocPtr plist = new_plist(); 627 xmlDocPtr plist = new_plist();
620 xmlNode *dict = add_child_to_plist(plist, "dict", "\n", NULL, 0); 628 xmlNode *dict = add_child_to_plist(plist, "dict", "\n", NULL, 0);
621 xmlNode *key; 629 xmlNode *key;
622 char *what2send = NULL, **dictionary = NULL; 630 char *what2send = NULL, **dictionary = NULL;
623 uint32 len = 0, bytes = 0, return_me = 0, i = 0; 631 uint32 len = 0, bytes = 0, return_me = 0, i = 0;
632 iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR;
624 // end variables 633 // end variables
625 634
626 key = add_key_str_dict_element(plist, dict, "HostID", HostID, 1); 635 key = add_key_str_dict_element(plist, dict, "HostID", HostID, 1);
627 if (!key) { 636 if (!key) {
628 if (debug) printf("Couldn't add a key.\n"); 637 if (debug) printf("Couldn't add a key.\n");
629 xmlFreeDoc(plist); 638 xmlFreeDoc(plist);
630 return 0; 639 return IPHONE_E_DICT_ERROR;
631 } 640 }
632 key = add_key_str_dict_element(plist, dict, "Request", "StartSession", 1); 641 key = add_key_str_dict_element(plist, dict, "Request", "StartSession", 1);
633 if (!key) { 642 if (!key) {
634 if (debug) printf("Couldn't add a key.\n"); 643 if (debug) printf("Couldn't add a key.\n");
635 xmlFreeDoc(plist); 644 xmlFreeDoc(plist);
636 return 0; 645 return IPHONE_E_DICT_ERROR;
637 } 646 }
638 647
639 xmlDocDumpMemory(plist, (xmlChar **)&what2send, &len); 648 xmlDocDumpMemory(plist, (xmlChar **)&what2send, &len);
640 bytes = iphone_lckd_send(control, what2send, len); 649 ret = iphone_lckd_send(control, what2send, len, &bytes);
641 650
642 xmlFree(what2send); 651 xmlFree(what2send);
643 xmlFreeDoc(plist); 652 xmlFreeDoc(plist);
653
654 if (ret != IPHONE_E_SUCCESS) return ret;
644 655
645 if (bytes > 0) { 656 if (bytes > 0) {
646 len = iphone_lckd_recv(control, &what2send); 657 ret = iphone_lckd_recv(control, &what2send, &len);
647 plist = xmlReadMemory(what2send, len, NULL, NULL, 0); 658 plist = xmlReadMemory(what2send, len, NULL, NULL, 0);
648 dict = xmlDocGetRootElement(plist); 659 dict = xmlDocGetRootElement(plist);
660 if (!dict) return IPHONE_E_DICT_ERROR;
649 for (dict = dict->children; dict; dict = dict->next) { 661 for (dict = dict->children; dict; dict = dict->next) {
650 if (!xmlStrcmp(dict->name, "dict")) break; 662 if (!xmlStrcmp(dict->name, "dict")) break;
651 } 663 }
@@ -699,10 +711,10 @@ int lockdownd_start_SSL_session(iphone_lckd_client_t control, const char *HostID
699 if (debug) printf("GnuTLS reported something wrong.\n"); 711 if (debug) printf("GnuTLS reported something wrong.\n");
700 gnutls_perror(return_me); 712 gnutls_perror(return_me);
701 if (debug) printf("oh.. errno says %s\n", strerror(errno)); 713 if (debug) printf("oh.. errno says %s\n", strerror(errno));
702 return 0; 714 return IPHONE_E_SSL_ERROR;
703 } else { 715 } else {
704 control->in_SSL = 1; 716 control->in_SSL = 1;
705 return 1; 717 return IPHONE_E_SUCCESS;
706 } 718 }
707 } 719 }
708 } 720 }
@@ -716,10 +728,10 @@ int lockdownd_start_SSL_session(iphone_lckd_client_t control, const char *HostID
716 } 728 }
717 729
718 free_dictionary(dictionary); 730 free_dictionary(dictionary);
719 return 0; 731 return IPHONE_E_SSL_ERROR;
720 } else { 732 } else {
721 if (debug) printf("Didn't get enough bytes.\n"); 733 if (debug) printf("Didn't get enough bytes.\n");
722 return 0; 734 return IPHONE_E_NOT_ENOUGH_DATA;
723 } 735 }
724} 736}
725 737
@@ -737,7 +749,7 @@ ssize_t lockdownd_secuwrite(gnutls_transport_ptr_t transport, char *buffer, size
737 control = (iphone_lckd_client_t)transport; 749 control = (iphone_lckd_client_t)transport;
738 if (debug) printf("lockdownd_secuwrite() called\n"); 750 if (debug) printf("lockdownd_secuwrite() called\n");
739 if (debug) printf("pre-send\nlength = %zi\n", length); 751 if (debug) printf("pre-send\nlength = %zi\n", length);
740 bytes = iphone_mux_send(control->connection, buffer, length); 752 iphone_mux_send(control->connection, buffer, length, &bytes);
741 if (debug) printf("post-send\nsent %i bytes\n", bytes); 753 if (debug) printf("post-send\nsent %i bytes\n", bytes);
742 if (debug) { 754 if (debug) {
743 FILE *my_ssl_packet = fopen("sslpacketwrite.out", "w+"); 755 FILE *my_ssl_packet = fopen("sslpacketwrite.out", "w+");
@@ -795,7 +807,7 @@ ssize_t lockdownd_securead(gnutls_transport_ptr_t transport, char *buffer, size_
795 char *recv_buffer = (char*)malloc(sizeof(char) * (length * 1000)); // ensuring nothing stupid happens 807 char *recv_buffer = (char*)malloc(sizeof(char) * (length * 1000)); // ensuring nothing stupid happens
796 808
797 if (debug) printf("pre-read\nclient wants %zi bytes\n", length); 809 if (debug) printf("pre-read\nclient wants %zi bytes\n", length);
798 bytes = iphone_mux_recv(control->connection, recv_buffer, (length * 1000)); 810 iphone_mux_recv(control->connection, recv_buffer, (length * 1000), &bytes);
799 if (debug) printf("post-read\nwe got %i bytes\n", bytes); 811 if (debug) printf("post-read\nwe got %i bytes\n", bytes);
800 if (debug && bytes < 0) { 812 if (debug && bytes < 0) {
801 printf("lockdownd_securead(): uh oh\n"); 813 printf("lockdownd_securead(): uh oh\n");
@@ -839,8 +851,9 @@ iphone_error_t iphone_lckd_start_service ( iphone_lckd_client_t client, const ch
839 if (!client->in_SSL && !lockdownd_start_SSL_session(client, host_id)) return IPHONE_E_SSL_ERROR; 851 if (!client->in_SSL && !lockdownd_start_SSL_session(client, host_id)) return IPHONE_E_SSL_ERROR;
840 852
841 char *XML_query, **dictionary; 853 char *XML_query, **dictionary;
842 uint32 length, i = 0, port_loc = 0; 854 uint32 length, i = 0, port_loc = 0, bytes = 0;
843 uint8 result = 0; 855 uint8 result = 0;
856 iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR;
844 857
845 free(host_id); 858 free(host_id);
846 host_id = NULL; 859 host_id = NULL;
@@ -855,16 +868,17 @@ iphone_error_t iphone_lckd_start_service ( iphone_lckd_client_t client, const ch
855 868
856 xmlDocDumpMemory(plist, (xmlChar **)&XML_query, &length); 869 xmlDocDumpMemory(plist, (xmlChar **)&XML_query, &length);
857 870
858 iphone_lckd_send(client, XML_query, length); 871 ret = iphone_lckd_send(client, XML_query, length, &bytes);
859 free(XML_query); 872 free(XML_query);
873 if (IPHONE_E_SUCCESS != ret) return ret;
860 874
861 length = iphone_lckd_recv(client, &XML_query); 875 ret = iphone_lckd_recv(client, &XML_query, &bytes);
862
863 xmlFreeDoc(plist); 876 xmlFreeDoc(plist);
877 if (IPHONE_E_SUCCESS != ret) return ret;
864 878
865 if (length <= 0) return IPHONE_E_NOT_ENOUGH_DATA; 879 if (bytes <= 0) return IPHONE_E_NOT_ENOUGH_DATA;
866 else { 880 else {
867 plist = xmlReadMemory(XML_query, length, NULL, NULL, 0); 881 plist = xmlReadMemory(XML_query, bytes, NULL, NULL, 0);
868 if (!plist) return IPHONE_E_UNKNOWN_ERROR; 882 if (!plist) return IPHONE_E_UNKNOWN_ERROR;
869 dict = xmlDocGetRootElement(plist); 883 dict = xmlDocGetRootElement(plist);
870 if (!dict) return IPHONE_E_UNKNOWN_ERROR; 884 if (!dict) return IPHONE_E_UNKNOWN_ERROR;
@@ -892,7 +906,7 @@ iphone_error_t iphone_lckd_start_service ( iphone_lckd_client_t client, const ch
892 906
893 if (debug) { 907 if (debug) {
894 printf("lockdownd_start_service(): DATA RECEIVED:\n\n"); 908 printf("lockdownd_start_service(): DATA RECEIVED:\n\n");
895 fwrite(XML_query, 1, length, stdout); 909 fwrite(XML_query, 1, bytes, stdout);
896 printf("end data received by lockdownd_start_service()\n"); 910 printf("end data received by lockdownd_start_service()\n");
897 } 911 }
898 912
diff --git a/src/lockdown.h b/src/lockdown.h
index f22d7db..62c453f 100644
--- a/src/lockdown.h
+++ b/src/lockdown.h
@@ -43,19 +43,17 @@ struct iphone_lckd_client_int {
43char *lockdownd_generate_hostid(); 43char *lockdownd_generate_hostid();
44 44
45iphone_lckd_client_t new_lockdownd_client(iphone_device_t phone); 45iphone_lckd_client_t new_lockdownd_client(iphone_device_t phone);
46int lockdownd_hello(iphone_lckd_client_t control); 46iphone_error_t lockdownd_hello(iphone_lckd_client_t control);
47int lockdownd_get_device_uid(iphone_lckd_client_t control, char **uid); 47iphone_error_t lockdownd_get_device_uid(iphone_lckd_client_t control, char **uid);
48int lockdownd_get_device_public_key(iphone_lckd_client_t control, char **public_key); 48iphone_error_t lockdownd_get_device_public_key(iphone_lckd_client_t control, char **public_key);
49 49
50int lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char **host_cert_b64, char **root_cert_b64); 50iphone_error_t lockdownd_gen_pair_cert(char *public_key_b64, char **device_cert_b64, char **host_cert_b64, char **root_cert_b64);
51int lockdownd_pair_device(iphone_lckd_client_t control, char *public_key, char *host_id); 51iphone_error_t lockdownd_pair_device(iphone_lckd_client_t control, char *public_key, char *host_id);
52int lockdownd_recv(iphone_lckd_client_t control, char **dump_data);
53int lockdownd_send(iphone_lckd_client_t control, char *raw_data, uint32 length);
54void lockdownd_close(iphone_lckd_client_t control); 52void lockdownd_close(iphone_lckd_client_t control);
55 53
56// SSL functions 54// SSL functions
57 55
58int lockdownd_start_SSL_session(iphone_lckd_client_t control, const char *HostID); 56iphone_error_t lockdownd_start_SSL_session(iphone_lckd_client_t control, const char *HostID);
59ssize_t lockdownd_securead(gnutls_transport_ptr_t transport, char *buffer, size_t length); 57ssize_t lockdownd_securead(gnutls_transport_ptr_t transport, char *buffer, size_t length);
60ssize_t lockdownd_secuwrite(gnutls_transport_ptr_t transport, char *buffer, size_t length); 58ssize_t lockdownd_secuwrite(gnutls_transport_ptr_t transport, char *buffer, size_t length);
61 59
diff --git a/src/main.c b/src/main.c
index 85405dd..fd8e0fe 100644
--- a/src/main.c
+++ b/src/main.c
@@ -56,27 +56,27 @@ int main(int argc, char *argv[]) {
56 } 56 }
57 57
58 char *uid = NULL; 58 char *uid = NULL;
59 if (lockdownd_get_device_uid(control, &uid)) { 59 if (IPHONE_E_SUCCESS == lockdownd_get_device_uid(control, &uid)) {
60 printf("DeviceUniqueID : %s\n", uid); 60 printf("DeviceUniqueID : %s\n", uid);
61 free(uid); 61 free(uid);
62 } 62 }
63 63
64 port = iphone_lckd_start_service(control, "com.apple.afc"); 64 iphone_lckd_start_service(control, "com.apple.afc", &port);
65 65
66 if (port) { 66 if (port) {
67 iphone_afc_client_t afc = NULL; 67 iphone_afc_client_t afc = NULL;
68 iphone_afc_new_client(phone, 3432, port, &afc); 68 iphone_afc_new_client(phone, 3432, port, &afc);
69 if (afc) { 69 if (afc) {
70 char **dirs; 70 char **dirs = NULL;
71 dirs = iphone_afc_get_dir_list(afc, "/eafaedf"); 71 iphone_afc_get_dir_list(afc, "/eafaedf", &dirs);
72 if (!dirs) dirs = iphone_afc_get_dir_list(afc, "/"); 72 if (!dirs) iphone_afc_get_dir_list(afc, "/", &dirs);
73 printf("Directory time.\n"); 73 printf("Directory time.\n");
74 for (i = 0; dirs[i]; i++) { 74 for (i = 0; dirs[i]; i++) {
75 printf("/%s\n", dirs[i]); 75 printf("/%s\n", dirs[i]);
76 } 76 }
77 77
78 g_strfreev(dirs); 78 g_strfreev(dirs);
79 dirs = iphone_afc_get_devinfo(afc); 79 iphone_afc_get_devinfo(afc, &dirs);
80 if (dirs) { 80 if (dirs) {
81 for (i = 0; dirs[i]; i+=2) { 81 for (i = 0; dirs[i]; i+=2) {
82 printf("%s: %s\n", dirs[i], dirs[i+1]); 82 printf("%s: %s\n", dirs[i], dirs[i+1]);
@@ -90,7 +90,7 @@ int main(int argc, char *argv[]) {
90 if (IPHONE_E_SUCCESS == iphone_afc_open_file(afc, "/iTunesOnTheGoPlaylist.plist", AFC_FILE_READ, &my_file) && my_file) { 90 if (IPHONE_E_SUCCESS == iphone_afc_open_file(afc, "/iTunesOnTheGoPlaylist.plist", AFC_FILE_READ, &my_file) && my_file) {
91 printf("A file size: %i\n", stbuf.st_size); 91 printf("A file size: %i\n", stbuf.st_size);
92 char *file_data = (char*)malloc(sizeof(char) * stbuf.st_size); 92 char *file_data = (char*)malloc(sizeof(char) * stbuf.st_size);
93 bytes = iphone_afc_read_file(afc, my_file, file_data, stbuf.st_size); 93 iphone_afc_read_file(afc, my_file, file_data, stbuf.st_size, &bytes);
94 if (bytes >= 0) { 94 if (bytes >= 0) {
95 printf("The file's data:\n"); 95 printf("The file's data:\n");
96 fwrite(file_data, 1, bytes, stdout); 96 fwrite(file_data, 1, bytes, stdout);
@@ -103,7 +103,7 @@ int main(int argc, char *argv[]) {
103 iphone_afc_open_file(afc, "/readme.libiphone.fx", AFC_FILE_WRITE, &my_file); 103 iphone_afc_open_file(afc, "/readme.libiphone.fx", AFC_FILE_WRITE, &my_file);
104 if (my_file) { 104 if (my_file) {
105 char *outdatafile = strdup("this is a bitchin text file\n"); 105 char *outdatafile = strdup("this is a bitchin text file\n");
106 bytes = iphone_afc_write_file(afc, my_file, outdatafile, strlen(outdatafile)); 106 iphone_afc_write_file(afc, my_file, outdatafile, strlen(outdatafile), &bytes);
107 free(outdatafile); 107 free(outdatafile);
108 if (bytes > 0) printf("Wrote a surprise. ;)\n"); 108 if (bytes > 0) printf("Wrote a surprise. ;)\n");
109 else printf("I wanted to write a surprise, but... :(\n"); 109 else printf("I wanted to write a surprise, but... :(\n");
@@ -121,10 +121,9 @@ int main(int argc, char *argv[]) {
121 121
122 printf("Seek & read\n"); 122 printf("Seek & read\n");
123 iphone_afc_open_file(afc, "/readme.libiphone.fx", AFC_FILE_READ, &my_file); 123 iphone_afc_open_file(afc, "/readme.libiphone.fx", AFC_FILE_READ, &my_file);
124 bytes = iphone_afc_seek_file(afc, my_file, 5); 124 if (IPHONE_E_SUCCESS != iphone_afc_seek_file(afc, my_file, 5)) printf("WARN: SEEK DID NOT WORK\n");
125 if (bytes) printf("WARN: SEEK DID NOT WORK\n");
126 char *threeletterword = (char*)malloc(sizeof(char) * 5); 125 char *threeletterword = (char*)malloc(sizeof(char) * 5);
127 bytes = iphone_afc_read_file(afc, my_file, threeletterword, 3); 126 iphone_afc_read_file(afc, my_file, threeletterword, 3, &bytes);
128 threeletterword[3] = '\0'; 127 threeletterword[3] = '\0';
129 if (bytes > 0) printf("Result: %s\n", threeletterword); 128 if (bytes > 0) printf("Result: %s\n", threeletterword);
130 else printf("Couldn't read!\n"); 129 else printf("Couldn't read!\n");
diff --git a/src/usbmux.c b/src/usbmux.c
index 8d85245..35f2ef3 100644
--- a/src/usbmux.c
+++ b/src/usbmux.c
@@ -250,7 +250,7 @@ iphone_error_t iphone_mux_send ( iphone_umux_client_t client, const char *data,
250 *sent_bytes = *sent_bytes - 28; // actual length sent. :/ 250 *sent_bytes = *sent_bytes - 28; // actual length sent. :/
251 } 251 }
252 252
253 return IPHONE_E_UNKNOWN_ERROR; 253 return IPHONE_E_SUCCESS;
254} 254}
255 255
256/** This is a higher-level USBMuxTCP-like function 256/** This is a higher-level USBMuxTCP-like function
@@ -371,6 +371,6 @@ iphone_error_t iphone_mux_recv ( iphone_umux_client_t client, char *data, uint32
371 371
372 // If we get to this point, 'tis probably bad. 372 // If we get to this point, 'tis probably bad.
373 if (debug) printf("mux_recv: Heisenbug: bytes and datalen not matching up\n"); 373 if (debug) printf("mux_recv: Heisenbug: bytes and datalen not matching up\n");
374 return -1; 374 return IPHONE_E_UNKNOWN_ERROR;
375} 375}
376 376