diff options
| author | 2009-07-25 03:26:39 +0200 | |
|---|---|---|
| committer | 2009-07-25 03:26:39 +0200 | |
| commit | 50be30047dbb0d38fd8d61763c13ec75d2b52543 (patch) | |
| tree | 87e021b478c6db6197294e4ef56c47cdad0f5992 /src | |
| parent | 1cfc2748d38eb97100cabced3b282108898099c2 (diff) | |
| download | libimobiledevice-50be30047dbb0d38fd8d61763c13ec75d2b52543.tar.gz libimobiledevice-50be30047dbb0d38fd8d61763c13ec75d2b52543.tar.bz2 | |
Update AFC API and use error codes from the STATUS operation response
Diffstat (limited to 'src')
| -rw-r--r-- | src/AFC.c | 306 | ||||
| -rw-r--r-- | src/AFC.h | 2 |
2 files changed, 153 insertions, 155 deletions
| @@ -23,13 +23,11 @@ | |||
| 23 | #include <stdlib.h> | 23 | #include <stdlib.h> |
| 24 | #include <errno.h> | 24 | #include <errno.h> |
| 25 | #include <unistd.h> | 25 | #include <unistd.h> |
| 26 | |||
| 26 | #include "AFC.h" | 27 | #include "AFC.h" |
| 27 | #include "iphone.h" | 28 | #include "iphone.h" |
| 28 | #include "utils.h" | 29 | #include "utils.h" |
| 29 | 30 | ||
| 30 | #include <libiphone/afc.h> | ||
| 31 | |||
| 32 | |||
| 33 | // This is the maximum size an AFC data packet can be | 31 | // This is the maximum size an AFC data packet can be |
| 34 | const int MAXIMUM_PACKET_SIZE = (2 << 15); | 32 | const int MAXIMUM_PACKET_SIZE = (2 << 15); |
| 35 | 33 | ||
| @@ -61,30 +59,30 @@ static void afc_unlock(afc_client_t client) | |||
| 61 | * | 59 | * |
| 62 | * @return A handle to the newly-connected client or NULL upon error. | 60 | * @return A handle to the newly-connected client or NULL upon error. |
| 63 | */ | 61 | */ |
| 64 | iphone_error_t afc_new_client(iphone_device_t device, int dst_port, afc_client_t * client) | 62 | afc_error_t afc_client_new(iphone_device_t device, int dst_port, afc_client_t * client) |
| 65 | { | 63 | { |
| 66 | //makes sure thread environment is available | 64 | /* makes sure thread environment is available */ |
| 67 | if (!g_thread_supported()) | 65 | if (!g_thread_supported()) |
| 68 | g_thread_init(NULL); | 66 | g_thread_init(NULL); |
| 69 | 67 | ||
| 70 | if (!device) | 68 | if (!device) |
| 71 | return IPHONE_E_INVALID_ARG; | 69 | return AFC_E_INVALID_ARGUMENT; |
| 72 | 70 | ||
| 73 | // Attempt connection | 71 | /* attempt connection */ |
| 74 | int sfd = usbmuxd_connect(device->handle, dst_port); | 72 | int sfd = usbmuxd_connect(device->handle, dst_port); |
| 75 | if (sfd < 0) { | 73 | if (sfd < 0) { |
| 76 | return IPHONE_E_UNKNOWN_ERROR; // ret; | 74 | return AFC_E_MUX_ERROR; |
| 77 | } | 75 | } |
| 78 | 76 | ||
| 79 | afc_client_t client_loc = (afc_client_t) malloc(sizeof(struct afc_client_int)); | 77 | afc_client_t client_loc = (afc_client_t) malloc(sizeof(struct afc_client_int)); |
| 80 | client_loc->sfd = sfd; | 78 | client_loc->sfd = sfd; |
| 81 | 79 | ||
| 82 | // Allocate a packet | 80 | /* allocate a packet */ |
| 83 | client_loc->afc_packet = (AFCPacket *) malloc(sizeof(AFCPacket)); | 81 | client_loc->afc_packet = (AFCPacket *) malloc(sizeof(AFCPacket)); |
| 84 | if (!client_loc->afc_packet) { | 82 | if (!client_loc->afc_packet) { |
| 85 | usbmuxd_disconnect(client_loc->sfd); | 83 | usbmuxd_disconnect(client_loc->sfd); |
| 86 | free(client_loc); | 84 | free(client_loc); |
| 87 | return IPHONE_E_UNKNOWN_ERROR; | 85 | return AFC_E_NO_MEM; |
| 88 | } | 86 | } |
| 89 | 87 | ||
| 90 | client_loc->afc_packet->packet_num = 0; | 88 | client_loc->afc_packet->packet_num = 0; |
| @@ -96,17 +94,17 @@ iphone_error_t afc_new_client(iphone_device_t device, int dst_port, afc_client_t | |||
| 96 | client_loc->mutex = g_mutex_new(); | 94 | client_loc->mutex = g_mutex_new(); |
| 97 | 95 | ||
| 98 | *client = client_loc; | 96 | *client = client_loc; |
| 99 | return IPHONE_E_SUCCESS; | 97 | return AFC_E_SUCCESS; |
| 100 | } | 98 | } |
| 101 | 99 | ||
| 102 | /** Disconnects an AFC client from the phone. | 100 | /** Disconnects an AFC client from the phone. |
| 103 | * | 101 | * |
| 104 | * @param client The client to disconnect. | 102 | * @param client The client to disconnect. |
| 105 | */ | 103 | */ |
| 106 | iphone_error_t afc_free_client(afc_client_t client) | 104 | afc_error_t afc_client_free(afc_client_t client) |
| 107 | { | 105 | { |
| 108 | if (!client || client->sfd < 0 || !client->afc_packet) | 106 | if (!client || client->sfd < 0 || !client->afc_packet) |
| 109 | return IPHONE_E_INVALID_ARG; | 107 | return AFC_E_INVALID_ARGUMENT; |
| 110 | 108 | ||
| 111 | usbmuxd_disconnect(client->sfd); | 109 | usbmuxd_disconnect(client->sfd); |
| 112 | free(client->afc_packet); | 110 | free(client->afc_packet); |
| @@ -214,13 +212,14 @@ int afc_get_errno(afc_client_t client) | |||
| 214 | * reason is that if you set them to different values, it indicates | 212 | * reason is that if you set them to different values, it indicates |
| 215 | * you want to send the data as two packets. | 213 | * you want to send the data as two packets. |
| 216 | */ | 214 | */ |
| 217 | static int dispatch_AFC_packet(afc_client_t client, const char *data, uint64_t length) | 215 | static int afc_dispatch_packet(afc_client_t client, const char *data, uint64_t length) |
| 218 | { | 216 | { |
| 219 | int bytes = 0, offset = 0; | 217 | int bytes = 0, offset = 0; |
| 220 | char *buffer; | 218 | char *buffer; |
| 221 | 219 | ||
| 222 | if (!client || client->sfd < 0 || !client->afc_packet) | 220 | if (!client || client->sfd < 0 || !client->afc_packet) |
| 223 | return 0; | 221 | return 0; |
| 222 | |||
| 224 | if (!data || !length) | 223 | if (!data || !length) |
| 225 | length = 0; | 224 | length = 0; |
| 226 | 225 | ||
| @@ -319,20 +318,20 @@ static int receive_AFC_data(afc_client_t client, char **dump_here) | |||
| 319 | return -1; | 318 | return -1; |
| 320 | } | 319 | } |
| 321 | 320 | ||
| 322 | // check if it's a valid AFC header | 321 | /* check if it's a valid AFC header */ |
| 323 | if (strncmp(header.magic, AFC_MAGIC, AFC_MAGIC_LEN)) { | 322 | if (strncmp(header.magic, AFC_MAGIC, AFC_MAGIC_LEN)) { |
| 324 | log_debug_msg("%s: Invalid AFC packet received (magic != " AFC_MAGIC ")!\n", __func__); | 323 | log_debug_msg("%s: Invalid AFC packet received (magic != " AFC_MAGIC ")!\n", __func__); |
| 325 | } | 324 | } |
| 326 | 325 | ||
| 327 | // check if it has the correct packet number | 326 | /* check if it has the correct packet number */ |
| 328 | if (header.packet_num != client->afc_packet->packet_num) { | 327 | if (header.packet_num != client->afc_packet->packet_num) { |
| 329 | // otherwise print a warning but do not abort | 328 | /* otherwise print a warning but do not abort */ |
| 330 | log_debug_msg("%s: ERROR: Unexpected packet number (%lld != %lld) aborting.\n", __func__, header.packet_num, client->afc_packet->packet_num); | 329 | log_debug_msg("%s: ERROR: Unexpected packet number (%lld != %lld) aborting.\n", __func__, header.packet_num, client->afc_packet->packet_num); |
| 331 | *dump_here = NULL; | 330 | *dump_here = NULL; |
| 332 | return -1; | 331 | return -1; |
| 333 | } | 332 | } |
| 334 | 333 | ||
| 335 | // then, read the attached packet | 334 | /* then, read the attached packet */ |
| 336 | if (header.this_length < sizeof(AFCPacket)) { | 335 | if (header.this_length < sizeof(AFCPacket)) { |
| 337 | log_debug_msg("%s: Invalid AFCPacket header received!\n", __func__); | 336 | log_debug_msg("%s: Invalid AFCPacket header received!\n", __func__); |
| 338 | *dump_here = NULL; | 337 | *dump_here = NULL; |
| @@ -354,7 +353,7 @@ static int receive_AFC_data(afc_client_t client, char **dump_here) | |||
| 354 | entire_len = (uint32_t)header.entire_length - sizeof(AFCPacket); | 353 | entire_len = (uint32_t)header.entire_length - sizeof(AFCPacket); |
| 355 | this_len = (uint32_t)header.this_length - sizeof(AFCPacket); | 354 | this_len = (uint32_t)header.this_length - sizeof(AFCPacket); |
| 356 | 355 | ||
| 357 | // this is here as a check (perhaps a different upper limit is good?) | 356 | /* this is here as a check (perhaps a different upper limit is good?) */ |
| 358 | if (entire_len > (uint32_t)MAXIMUM_PACKET_SIZE) { | 357 | if (entire_len > (uint32_t)MAXIMUM_PACKET_SIZE) { |
| 359 | fprintf(stderr, "%s: entire_len is larger than MAXIMUM_PACKET_SIZE, (%d > %d)!\n", __func__, entire_len, MAXIMUM_PACKET_SIZE); | 358 | fprintf(stderr, "%s: entire_len is larger than MAXIMUM_PACKET_SIZE, (%d > %d)!\n", __func__, entire_len, MAXIMUM_PACKET_SIZE); |
| 360 | } | 359 | } |
| @@ -469,14 +468,14 @@ static char **make_strings_list(char *tokens, int true_length) | |||
| 469 | * @return A char ** list of files in that directory, terminated by an empty | 468 | * @return A char ** list of files in that directory, terminated by an empty |
| 470 | * string for now or NULL if there was an error. | 469 | * string for now or NULL if there was an error. |
| 471 | */ | 470 | */ |
| 472 | iphone_error_t afc_get_dir_list(afc_client_t client, const char *dir, char ***list) | 471 | afc_error_t afc_read_directory(afc_client_t client, const char *dir, char ***list) |
| 473 | { | 472 | { |
| 474 | int bytes = 0; | 473 | int bytes = 0; |
| 475 | char *data = NULL, **list_loc = NULL; | 474 | char *data = NULL, **list_loc = NULL; |
| 476 | iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR; | 475 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; |
| 477 | 476 | ||
| 478 | if (!client || !dir || !list || (list && *list)) | 477 | if (!client || !dir || !list || (list && *list)) |
| 479 | return IPHONE_E_INVALID_ARG; | 478 | return AFC_E_INVALID_ARGUMENT; |
| 480 | 479 | ||
| 481 | afc_lock(client); | 480 | afc_lock(client); |
| 482 | 481 | ||
| @@ -484,10 +483,10 @@ iphone_error_t afc_get_dir_list(afc_client_t client, const char *dir, char ***li | |||
| 484 | client->afc_packet->operation = AFC_OP_READ_DIR; | 483 | client->afc_packet->operation = AFC_OP_READ_DIR; |
| 485 | client->afc_packet->entire_length = 0; | 484 | client->afc_packet->entire_length = 0; |
| 486 | client->afc_packet->this_length = 0; | 485 | client->afc_packet->this_length = 0; |
| 487 | bytes = dispatch_AFC_packet(client, dir, strlen(dir)+1); | 486 | bytes = afc_dispatch_packet(client, dir, strlen(dir)+1); |
| 488 | if (bytes <= 0) { | 487 | if (bytes <= 0) { |
| 489 | afc_unlock(client); | 488 | afc_unlock(client); |
| 490 | return IPHONE_E_NOT_ENOUGH_DATA; | 489 | return AFC_E_NOT_ENOUGH_DATA; |
| 491 | } | 490 | } |
| 492 | // Receive the data | 491 | // Receive the data |
| 493 | bytes = receive_AFC_data(client, &data); | 492 | bytes = receive_AFC_data(client, &data); |
| @@ -515,23 +514,24 @@ iphone_error_t afc_get_dir_list(afc_client_t client, const char *dir, char ***li | |||
| 515 | * @return A char ** list of parameters as given by AFC or NULL if there was an | 514 | * @return A char ** list of parameters as given by AFC or NULL if there was an |
| 516 | * error. | 515 | * error. |
| 517 | */ | 516 | */ |
| 518 | iphone_error_t afc_get_devinfo(afc_client_t client, char ***infos) | 517 | afc_error_t afc_get_device_info(afc_client_t client, char ***infos) |
| 519 | { | 518 | { |
| 520 | int bytes = 0; | 519 | int bytes = 0; |
| 521 | char *data = NULL, **list = NULL; | 520 | char *data = NULL, **list = NULL; |
| 521 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 522 | 522 | ||
| 523 | if (!client || !infos) | 523 | if (!client || !infos) |
| 524 | return IPHONE_E_INVALID_ARG; | 524 | return AFC_E_INVALID_ARGUMENT; |
| 525 | 525 | ||
| 526 | afc_lock(client); | 526 | afc_lock(client); |
| 527 | 527 | ||
| 528 | // Send the command | 528 | // Send the command |
| 529 | client->afc_packet->operation = AFC_OP_GET_DEVINFO; | 529 | client->afc_packet->operation = AFC_OP_GET_DEVINFO; |
| 530 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; | 530 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; |
| 531 | bytes = dispatch_AFC_packet(client, NULL, 0); | 531 | bytes = afc_dispatch_packet(client, NULL, 0); |
| 532 | if (bytes < 0) { | 532 | if (bytes < 0) { |
| 533 | afc_unlock(client); | 533 | afc_unlock(client); |
| 534 | return IPHONE_E_NOT_ENOUGH_DATA; | 534 | return AFC_E_NOT_ENOUGH_DATA; |
| 535 | } | 535 | } |
| 536 | // Receive the data | 536 | // Receive the data |
| 537 | bytes = receive_AFC_data(client, &data); | 537 | bytes = receive_AFC_data(client, &data); |
| @@ -547,34 +547,36 @@ iphone_error_t afc_get_devinfo(afc_client_t client, char ***infos) | |||
| 547 | afc_unlock(client); | 547 | afc_unlock(client); |
| 548 | 548 | ||
| 549 | *infos = list; | 549 | *infos = list; |
| 550 | return IPHONE_E_SUCCESS; | 550 | |
| 551 | return ret; | ||
| 551 | } | 552 | } |
| 552 | 553 | ||
| 553 | /** Deletes a file. | 554 | /** Deletes a file or directory. |
| 554 | * | 555 | * |
| 555 | * @param client The client to have delete the file. | 556 | * @param client The client to use. |
| 556 | * @param path The file to delete. (must be a fully-qualified path) | 557 | * @param path The path to delete. (must be a fully-qualified path) |
| 557 | * | 558 | * |
| 558 | * @return IPHONE_E_SUCCESS if everythong went well, IPHONE_E_INVALID_ARG | 559 | * @return AFC_E_SUCCESS if everythong went well, AFC_E_INVALID_ARGUMENT |
| 559 | * if arguments are NULL or invalid, IPHONE_E_NOT_ENOUGH_DATA otherwise. | 560 | * if arguments are NULL or invalid, AFC_E_NOT_ENOUGH_DATA otherwise. |
| 560 | */ | 561 | */ |
| 561 | iphone_error_t afc_delete_file(afc_client_t client, const char *path) | 562 | afc_error_t afc_remove_path(afc_client_t client, const char *path) |
| 562 | { | 563 | { |
| 563 | char *response = NULL; | 564 | char *response = NULL; |
| 564 | int bytes; | 565 | int bytes; |
| 566 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 565 | 567 | ||
| 566 | if (!client || !path || !client->afc_packet || client->sfd < 0) | 568 | if (!client || !path || !client->afc_packet || client->sfd < 0) |
| 567 | return IPHONE_E_INVALID_ARG; | 569 | return AFC_E_INVALID_ARGUMENT; |
| 568 | 570 | ||
| 569 | afc_lock(client); | 571 | afc_lock(client); |
| 570 | 572 | ||
| 571 | // Send command | 573 | // Send command |
| 572 | client->afc_packet->this_length = client->afc_packet->entire_length = 0; | 574 | client->afc_packet->this_length = client->afc_packet->entire_length = 0; |
| 573 | client->afc_packet->operation = AFC_OP_REMOVE_PATH; | 575 | client->afc_packet->operation = AFC_OP_REMOVE_PATH; |
| 574 | bytes = dispatch_AFC_packet(client, path, strlen(path)+1); | 576 | bytes = afc_dispatch_packet(client, path, strlen(path)+1); |
| 575 | if (bytes <= 0) { | 577 | if (bytes <= 0) { |
| 576 | afc_unlock(client); | 578 | afc_unlock(client); |
| 577 | return IPHONE_E_NOT_ENOUGH_DATA; | 579 | return AFC_E_NOT_ENOUGH_DATA; |
| 578 | } | 580 | } |
| 579 | // Receive response | 581 | // Receive response |
| 580 | bytes = receive_AFC_data(client, &response); | 582 | bytes = receive_AFC_data(client, &response); |
| @@ -583,29 +585,27 @@ iphone_error_t afc_delete_file(afc_client_t client, const char *path) | |||
| 583 | 585 | ||
| 584 | afc_unlock(client); | 586 | afc_unlock(client); |
| 585 | 587 | ||
| 586 | if (bytes < 0) { | 588 | return ret; |
| 587 | return IPHONE_E_AFC_ERROR; | ||
| 588 | } | ||
| 589 | return IPHONE_E_SUCCESS; | ||
| 590 | } | 589 | } |
| 591 | 590 | ||
| 592 | /** Renames a file on the phone. | 591 | /** Renames a file or directory on the phone. |
| 593 | * | 592 | * |
| 594 | * @param client The client to have rename the file. | 593 | * @param client The client to have rename. |
| 595 | * @param from The file to rename. (must be a fully-qualified path) | 594 | * @param from The name to rename from. (must be a fully-qualified path) |
| 596 | * @param to The new name of the file. (must also be a fully-qualified path) | 595 | * @param to The new name. (must also be a fully-qualified path) |
| 597 | * | 596 | * |
| 598 | * @return IPHONE_E_SUCCESS if everythong went well, IPHONE_E_INVALID_ARG | 597 | * @return AFC_E_SUCCESS if everythong went well, AFC_E_INVALID_ARGUMENT |
| 599 | * if arguments are NULL or invalid, IPHONE_E_NOT_ENOUGH_DATA otherwise. | 598 | * if arguments are NULL or invalid, AFC_E_NOT_ENOUGH_DATA otherwise. |
| 600 | */ | 599 | */ |
| 601 | iphone_error_t afc_rename_file(afc_client_t client, const char *from, const char *to) | 600 | afc_error_t afc_rename_path(afc_client_t client, const char *from, const char *to) |
| 602 | { | 601 | { |
| 603 | char *response = NULL; | 602 | char *response = NULL; |
| 604 | char *send = (char *) malloc(sizeof(char) * (strlen(from) + strlen(to) + 1 + sizeof(uint32_t))); | 603 | char *send = (char *) malloc(sizeof(char) * (strlen(from) + strlen(to) + 1 + sizeof(uint32_t))); |
| 605 | int bytes = 0; | 604 | int bytes = 0; |
| 605 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 606 | 606 | ||
| 607 | if (!client || !from || !to || !client->afc_packet || client->sfd < 0) | 607 | if (!client || !from || !to || !client->afc_packet || client->sfd < 0) |
| 608 | return IPHONE_E_INVALID_ARG; | 608 | return AFC_E_INVALID_ARGUMENT; |
| 609 | 609 | ||
| 610 | afc_lock(client); | 610 | afc_lock(client); |
| 611 | 611 | ||
| @@ -614,11 +614,11 @@ iphone_error_t afc_rename_file(afc_client_t client, const char *from, const char | |||
| 614 | memcpy(send + strlen(from) + 1, to, strlen(to) + 1); | 614 | memcpy(send + strlen(from) + 1, to, strlen(to) + 1); |
| 615 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; | 615 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; |
| 616 | client->afc_packet->operation = AFC_OP_RENAME_PATH; | 616 | client->afc_packet->operation = AFC_OP_RENAME_PATH; |
| 617 | bytes = dispatch_AFC_packet(client, send, strlen(to)+1 + strlen(from)+1); | 617 | bytes = afc_dispatch_packet(client, send, strlen(to)+1 + strlen(from)+1); |
| 618 | free(send); | 618 | free(send); |
| 619 | if (bytes <= 0) { | 619 | if (bytes <= 0) { |
| 620 | afc_unlock(client); | 620 | afc_unlock(client); |
| 621 | return IPHONE_E_NOT_ENOUGH_DATA; | 621 | return AFC_E_NOT_ENOUGH_DATA; |
| 622 | } | 622 | } |
| 623 | // Receive response | 623 | // Receive response |
| 624 | bytes = receive_AFC_data(client, &response); | 624 | bytes = receive_AFC_data(client, &response); |
| @@ -627,10 +627,7 @@ iphone_error_t afc_rename_file(afc_client_t client, const char *from, const char | |||
| 627 | 627 | ||
| 628 | afc_unlock(client); | 628 | afc_unlock(client); |
| 629 | 629 | ||
| 630 | if (bytes < 0) { | 630 | return ret; |
| 631 | return IPHONE_E_AFC_ERROR; | ||
| 632 | } | ||
| 633 | return IPHONE_E_SUCCESS; | ||
| 634 | } | 631 | } |
| 635 | 632 | ||
| 636 | /** Creates a directory on the phone. | 633 | /** Creates a directory on the phone. |
| @@ -639,26 +636,27 @@ iphone_error_t afc_rename_file(afc_client_t client, const char *from, const char | |||
| 639 | * @param dir The directory's path. (must be a fully-qualified path, I assume | 636 | * @param dir The directory's path. (must be a fully-qualified path, I assume |
| 640 | * all other mkdir restrictions apply as well) | 637 | * all other mkdir restrictions apply as well) |
| 641 | * | 638 | * |
| 642 | * @return IPHONE_E_SUCCESS if everythong went well, IPHONE_E_INVALID_ARG | 639 | * @return AFC_E_SUCCESS if everythong went well, AFC_E_INVALID_ARGUMENT |
| 643 | * if arguments are NULL or invalid, IPHONE_E_NOT_ENOUGH_DATA otherwise. | 640 | * if arguments are NULL or invalid, AFC_E_NOT_ENOUGH_DATA otherwise. |
| 644 | */ | 641 | */ |
| 645 | iphone_error_t afc_mkdir(afc_client_t client, const char *dir) | 642 | afc_error_t afc_make_directory(afc_client_t client, const char *dir) |
| 646 | { | 643 | { |
| 647 | int bytes = 0; | 644 | int bytes = 0; |
| 648 | char *response = NULL; | 645 | char *response = NULL; |
| 646 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 649 | 647 | ||
| 650 | if (!client) | 648 | if (!client) |
| 651 | return IPHONE_E_INVALID_ARG; | 649 | return AFC_E_INVALID_ARGUMENT; |
| 652 | 650 | ||
| 653 | afc_lock(client); | 651 | afc_lock(client); |
| 654 | 652 | ||
| 655 | // Send command | 653 | // Send command |
| 656 | client->afc_packet->operation = AFC_OP_MAKE_DIR; | 654 | client->afc_packet->operation = AFC_OP_MAKE_DIR; |
| 657 | client->afc_packet->this_length = client->afc_packet->entire_length = 0; | 655 | client->afc_packet->this_length = client->afc_packet->entire_length = 0; |
| 658 | bytes = dispatch_AFC_packet(client, dir, strlen(dir)+1); | 656 | bytes = afc_dispatch_packet(client, dir, strlen(dir)+1); |
| 659 | if (bytes <= 0) { | 657 | if (bytes <= 0) { |
| 660 | afc_unlock(client); | 658 | afc_unlock(client); |
| 661 | return IPHONE_E_NOT_ENOUGH_DATA; | 659 | return AFC_E_NOT_ENOUGH_DATA; |
| 662 | } | 660 | } |
| 663 | // Receive response | 661 | // Receive response |
| 664 | bytes = receive_AFC_data(client, &response); | 662 | bytes = receive_AFC_data(client, &response); |
| @@ -667,10 +665,7 @@ iphone_error_t afc_mkdir(afc_client_t client, const char *dir) | |||
| 667 | 665 | ||
| 668 | afc_unlock(client); | 666 | afc_unlock(client); |
| 669 | 667 | ||
| 670 | if (bytes < 0) { | 668 | return ret; |
| 671 | return IPHONE_E_AFC_ERROR; | ||
| 672 | } | ||
| 673 | return IPHONE_E_SUCCESS; | ||
| 674 | } | 669 | } |
| 675 | 670 | ||
| 676 | /** Gets information about a specific file. | 671 | /** Gets information about a specific file. |
| @@ -681,38 +676,37 @@ iphone_error_t afc_mkdir(afc_client_t client, const char *dir) | |||
| 681 | * list of strings with the file information. | 676 | * list of strings with the file information. |
| 682 | * Set to NULL before calling this function. | 677 | * Set to NULL before calling this function. |
| 683 | * | 678 | * |
| 684 | * @return IPHONE_E_SUCCESS on success or an IPHONE_E_* error value | 679 | * @return AFC_E_SUCCESS on success or an AFC_E_* error value |
| 685 | * when something went wrong. | 680 | * when something went wrong. |
| 686 | */ | 681 | */ |
| 687 | iphone_error_t afc_get_file_info(afc_client_t client, const char *path, char ***infolist) | 682 | afc_error_t afc_get_file_info(afc_client_t client, const char *path, char ***infolist) |
| 688 | { | 683 | { |
| 689 | char *received = NULL; | 684 | char *received = NULL; |
| 690 | int length; | 685 | int bytes; |
| 686 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 691 | 687 | ||
| 692 | if (!client || !path || !infolist) { | 688 | if (!client || !path || !infolist) |
| 693 | return IPHONE_E_INVALID_ARG; | 689 | return AFC_E_INVALID_ARGUMENT; |
| 694 | } | ||
| 695 | 690 | ||
| 696 | afc_lock(client); | 691 | afc_lock(client); |
| 697 | 692 | ||
| 698 | // Send command | 693 | // Send command |
| 699 | client->afc_packet->operation = AFC_OP_GET_FILE_INFO; | 694 | client->afc_packet->operation = AFC_OP_GET_FILE_INFO; |
| 700 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; | 695 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; |
| 701 | dispatch_AFC_packet(client, path, strlen(path)+1); | 696 | afc_dispatch_packet(client, path, strlen(path)+1); |
| 702 | 697 | ||
| 703 | // Receive data | 698 | // Receive data |
| 704 | length = receive_AFC_data(client, &received); | 699 | length = receive_AFC_data(client, &received); |
| 705 | if (received) { | 700 | if (received) { |
| 706 | *infolist = make_strings_list(received, length); | 701 | *infolist = make_strings_list(received, bytes); |
| 707 | free(received); | 702 | free(received); |
| 708 | } else { | ||
| 709 | afc_unlock(client); | ||
| 710 | return IPHONE_E_AFC_ERROR; | ||
| 711 | } | 703 | } |
| 712 | 704 | ||
| 705 | log_debug_msg("%s: Didn't get any further data\n", __func__); | ||
| 706 | |||
| 713 | afc_unlock(client); | 707 | afc_unlock(client); |
| 714 | 708 | ||
| 715 | return IPHONE_E_SUCCESS; | 709 | return ret; |
| 716 | } | 710 | } |
| 717 | 711 | ||
| 718 | /** Opens a file on the phone. | 712 | /** Opens a file on the phone. |
| @@ -725,21 +719,22 @@ iphone_error_t afc_get_file_info(afc_client_t client, const char *path, char *** | |||
| 725 | * destroying anything previously there. | 719 | * destroying anything previously there. |
| 726 | * @param handle Pointer to a uint64_t that will hold the handle of the file | 720 | * @param handle Pointer to a uint64_t that will hold the handle of the file |
| 727 | * | 721 | * |
| 728 | * @return IPHONE_E_SUCCESS on success or an IPHONE_E_* error on failure. | 722 | * @return AFC_E_SUCCESS on success or an AFC_E_* error on failure. |
| 729 | */ | 723 | */ |
| 730 | iphone_error_t | 724 | iphone_error_t |
| 731 | afc_open_file(afc_client_t client, const char *filename, | 725 | afc_file_open(afc_client_t client, const char *filename, |
| 732 | afc_file_mode_t file_mode, uint64_t *handle) | 726 | afc_file_mode_t file_mode, uint64_t *handle) |
| 733 | { | 727 | { |
| 734 | uint32_t ag = 0; | 728 | uint32_t ag = 0; |
| 735 | int bytes = 0, length = 0; | 729 | int bytes = 0; |
| 736 | char *data = (char *) malloc(sizeof(char) * (8 + strlen(filename) + 1)); | 730 | char *data = (char *) malloc(sizeof(char) * (8 + strlen(filename) + 1)); |
| 731 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 737 | 732 | ||
| 738 | // set handle to 0 so in case an error occurs, the handle is invalid | 733 | // set handle to 0 so in case an error occurs, the handle is invalid |
| 739 | *handle = 0; | 734 | *handle = 0; |
| 740 | 735 | ||
| 741 | if (!client || client->sfd < 0|| !client->afc_packet) | 736 | if (!client || client->sfd < 0|| !client->afc_packet) |
| 742 | return IPHONE_E_INVALID_ARG; | 737 | return AFC_E_INVALID_ARGUMENT; |
| 743 | 738 | ||
| 744 | afc_lock(client); | 739 | afc_lock(client); |
| 745 | 740 | ||
| @@ -750,13 +745,13 @@ afc_open_file(afc_client_t client, const char *filename, | |||
| 750 | data[8 + strlen(filename)] = '\0'; | 745 | data[8 + strlen(filename)] = '\0'; |
| 751 | client->afc_packet->operation = AFC_OP_FILE_OPEN; | 746 | client->afc_packet->operation = AFC_OP_FILE_OPEN; |
| 752 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; | 747 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; |
| 753 | bytes = dispatch_AFC_packet(client, data, 8 + strlen(filename) + 1); | 748 | bytes = afc_dispatch_packet(client, data, 8 + strlen(filename) + 1); |
| 754 | free(data); | 749 | free(data); |
| 755 | 750 | ||
| 756 | if (bytes <= 0) { | 751 | if (bytes <= 0) { |
| 757 | log_debug_msg("%s: Didn't receive a response to the command\n", __func__); | 752 | log_debug_msg("%s: Didn't receive a response to the command\n", __func__); |
| 758 | afc_unlock(client); | 753 | afc_unlock(client); |
| 759 | return IPHONE_E_NOT_ENOUGH_DATA; | 754 | return AFC_E_NOT_ENOUGH_DATA; |
| 760 | } | 755 | } |
| 761 | // Receive the data | 756 | // Receive the data |
| 762 | length = receive_AFC_data(client, &data); | 757 | length = receive_AFC_data(client, &data); |
| @@ -766,16 +761,12 @@ afc_open_file(afc_client_t client, const char *filename, | |||
| 766 | // Get the file handle | 761 | // Get the file handle |
| 767 | memcpy(handle, data, sizeof(uint64_t)); | 762 | memcpy(handle, data, sizeof(uint64_t)); |
| 768 | free(data); | 763 | free(data); |
| 769 | return IPHONE_E_SUCCESS; | 764 | return ret; |
| 770 | } else { | ||
| 771 | log_debug_msg("afc_open_file: Didn't get any further data\n"); | ||
| 772 | afc_unlock(client); | ||
| 773 | return IPHONE_E_AFC_ERROR; | ||
| 774 | } | 765 | } |
| 775 | 766 | ||
| 776 | afc_unlock(client); | 767 | afc_unlock(client); |
| 777 | 768 | ||
| 778 | return IPHONE_E_UNKNOWN_ERROR; | 769 | return ret; |
| 779 | } | 770 | } |
| 780 | 771 | ||
| 781 | /** Attempts to the read the given number of bytes from the given file. | 772 | /** Attempts to the read the given number of bytes from the given file. |
| @@ -788,20 +779,21 @@ afc_open_file(afc_client_t client, const char *filename, | |||
| 788 | * @return The number of bytes read if successful. If there was an error -1. | 779 | * @return The number of bytes read if successful. If there was an error -1. |
| 789 | */ | 780 | */ |
| 790 | iphone_error_t | 781 | iphone_error_t |
| 791 | afc_read_file(afc_client_t client, uint64_t handle, char *data, int length, uint32_t * bytes) | 782 | afc_file_read(afc_client_t client, uint64_t handle, char *data, int length, uint32_t * bytes) |
| 792 | { | 783 | { |
| 793 | char *input = NULL; | 784 | char *input = NULL; |
| 794 | int current_count = 0, bytes_loc = 0; | 785 | int current_count = 0, bytes_loc = 0; |
| 795 | const int MAXIMUM_READ_SIZE = 1 << 16; | 786 | const int MAXIMUM_READ_SIZE = 1 << 16; |
| 787 | afc_error_t ret = AFC_E_SUCCESS; | ||
| 796 | 788 | ||
| 797 | if (!client || !client->afc_packet || client->sfd < 0 || handle == 0) | 789 | if (!client || !client->afc_packet || client->sfd < 0 || handle == 0) |
| 798 | return IPHONE_E_INVALID_ARG; | 790 | return AFC_E_INVALID_ARGUMENT; |
| 799 | log_debug_msg("%s: called for length %i\n", __func__, length); | 791 | log_debug_msg("%s: called for length %i\n", __func__, length); |
| 800 | 792 | ||
| 801 | afc_lock(client); | 793 | afc_lock(client); |
| 802 | 794 | ||
| 803 | // Looping here to get around the maximum amount of data that | 795 | // Looping here to get around the maximum amount of data that |
| 804 | // recieve_AFC_data can handle | 796 | // afc_receive_data can handle |
| 805 | while (current_count < length) { | 797 | while (current_count < length) { |
| 806 | log_debug_msg("%s: current count is %i but length is %i\n", __func__, current_count, length); | 798 | log_debug_msg("%s: current count is %i but length is %i\n", __func__, current_count, length); |
| 807 | 799 | ||
| @@ -811,26 +803,26 @@ afc_read_file(afc_client_t client, uint64_t handle, char *data, int length, uint | |||
| 811 | packet->size = ((length - current_count) < MAXIMUM_READ_SIZE) ? (length - current_count) : MAXIMUM_READ_SIZE; | 803 | packet->size = ((length - current_count) < MAXIMUM_READ_SIZE) ? (length - current_count) : MAXIMUM_READ_SIZE; |
| 812 | client->afc_packet->operation = AFC_OP_READ; | 804 | client->afc_packet->operation = AFC_OP_READ; |
| 813 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; | 805 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; |
| 814 | bytes_loc = dispatch_AFC_packet(client, (char *) packet, sizeof(AFCFilePacket)); | 806 | bytes_loc = afc_dispatch_packet(client, (char *) packet, sizeof(AFCFilePacket)); |
| 815 | free(packet); | 807 | free(packet); |
| 816 | 808 | ||
| 817 | if (bytes_loc <= 0) { | 809 | if (bytes_loc <= 0) { |
| 818 | afc_unlock(client); | 810 | afc_unlock(client); |
| 819 | return IPHONE_E_NOT_ENOUGH_DATA; | 811 | return AFC_E_NOT_ENOUGH_DATA; |
| 820 | } | 812 | } |
| 821 | // Receive the data | 813 | // Receive the data |
| 822 | bytes_loc = receive_AFC_data(client, &input); | 814 | bytes_loc = receive_AFC_data(client, &input); |
| 823 | log_debug_msg("%s: bytes returned: %i\n", __func__, bytes_loc); | 815 | log_debug_msg("%s: bytes returned: %i\n", __func__, bytes_loc); |
| 824 | if (bytes_loc < 0) { | 816 | if (bytes_loc < 0) { |
| 825 | afc_unlock(client); | 817 | afc_unlock(client); |
| 826 | return IPHONE_E_AFC_ERROR; | 818 | return ret; |
| 827 | } else if (bytes_loc == 0) { | 819 | } else if (bytes_loc == 0) { |
| 828 | if (input) | 820 | if (input) |
| 829 | free(input); | 821 | free(input); |
| 830 | afc_unlock(client); | 822 | afc_unlock(client); |
| 831 | *bytes = current_count; | 823 | *bytes = current_count; |
| 832 | return IPHONE_E_SUCCESS; // FIXME check that's actually a | 824 | /* FIXME: check that's actually a success */ |
| 833 | // success | 825 | return ret; |
| 834 | } else { | 826 | } else { |
| 835 | if (input) { | 827 | if (input) { |
| 836 | log_debug_msg("%s: %d\n", __func__, bytes_loc); | 828 | log_debug_msg("%s: %d\n", __func__, bytes_loc); |
| @@ -845,7 +837,7 @@ afc_read_file(afc_client_t client, uint64_t handle, char *data, int length, uint | |||
| 845 | 837 | ||
| 846 | afc_unlock(client); | 838 | afc_unlock(client); |
| 847 | *bytes = current_count; | 839 | *bytes = current_count; |
| 848 | return IPHONE_E_SUCCESS; | 840 | return ret; |
| 849 | } | 841 | } |
| 850 | 842 | ||
| 851 | /** Writes a given number of bytes to a file. | 843 | /** Writes a given number of bytes to a file. |
| @@ -859,7 +851,7 @@ afc_read_file(afc_client_t client, uint64_t handle, char *data, int length, uint | |||
| 859 | * none were written... | 851 | * none were written... |
| 860 | */ | 852 | */ |
| 861 | iphone_error_t | 853 | iphone_error_t |
| 862 | afc_write_file(afc_client_t client, uint64_t handle, | 854 | afc_file_write(afc_client_t client, uint64_t handle, |
| 863 | const char *data, int length, uint32_t * bytes) | 855 | const char *data, int length, uint32_t * bytes) |
| 864 | { | 856 | { |
| 865 | char *acknowledgement = NULL; | 857 | char *acknowledgement = NULL; |
| @@ -868,9 +860,10 @@ afc_write_file(afc_client_t client, uint64_t handle, | |||
| 868 | uint32_t segments = (length / MAXIMUM_WRITE_SIZE); | 860 | uint32_t segments = (length / MAXIMUM_WRITE_SIZE); |
| 869 | int bytes_loc = 0; | 861 | int bytes_loc = 0; |
| 870 | char *out_buffer = NULL; | 862 | char *out_buffer = NULL; |
| 863 | afc_error_t ret = AFC_E_SUCCESS; | ||
| 871 | 864 | ||
| 872 | if (!client || !client->afc_packet || client->sfd < 0 || !bytes || (handle == 0)) | 865 | if (!client || !client->afc_packet || client->sfd < 0 || !bytes || (handle == 0)) |
| 873 | return IPHONE_E_INVALID_ARG; | 866 | return AFC_E_INVALID_ARGUMENT; |
| 874 | 867 | ||
| 875 | afc_lock(client); | 868 | afc_lock(client); |
| 876 | 869 | ||
| @@ -885,10 +878,10 @@ afc_write_file(afc_client_t client, uint64_t handle, | |||
| 885 | out_buffer = (char *) malloc(sizeof(char) * client->afc_packet->entire_length - sizeof(AFCPacket)); | 878 | out_buffer = (char *) malloc(sizeof(char) * client->afc_packet->entire_length - sizeof(AFCPacket)); |
| 886 | memcpy(out_buffer, (char *)&handle, sizeof(uint64_t)); | 879 | memcpy(out_buffer, (char *)&handle, sizeof(uint64_t)); |
| 887 | memcpy(out_buffer + 8, data + current_count, MAXIMUM_WRITE_SIZE); | 880 | memcpy(out_buffer + 8, data + current_count, MAXIMUM_WRITE_SIZE); |
| 888 | bytes_loc = dispatch_AFC_packet(client, out_buffer, MAXIMUM_WRITE_SIZE + 8); | 881 | bytes_loc = afc_dispatch_packet(client, out_buffer, MAXIMUM_WRITE_SIZE + 8); |
| 889 | if (bytes_loc < 0) { | 882 | if (bytes_loc < 0) { |
| 890 | afc_unlock(client); | 883 | afc_unlock(client); |
| 891 | return IPHONE_E_NOT_ENOUGH_DATA; | 884 | return AFC_E_NOT_ENOUGH_DATA; |
| 892 | } | 885 | } |
| 893 | free(out_buffer); | 886 | free(out_buffer); |
| 894 | out_buffer = NULL; | 887 | out_buffer = NULL; |
| @@ -897,7 +890,7 @@ afc_write_file(afc_client_t client, uint64_t handle, | |||
| 897 | bytes_loc = receive_AFC_data(client, &acknowledgement); | 890 | bytes_loc = receive_AFC_data(client, &acknowledgement); |
| 898 | if (bytes_loc < 0) { | 891 | if (bytes_loc < 0) { |
| 899 | afc_unlock(client); | 892 | afc_unlock(client); |
| 900 | return IPHONE_E_AFC_ERROR; | 893 | return ret; |
| 901 | } else { | 894 | } else { |
| 902 | free(acknowledgement); | 895 | free(acknowledgement); |
| 903 | } | 896 | } |
| @@ -910,7 +903,7 @@ afc_write_file(afc_client_t client, uint64_t handle, | |||
| 910 | if (current_count == (uint32_t)length) { | 903 | if (current_count == (uint32_t)length) { |
| 911 | afc_unlock(client); | 904 | afc_unlock(client); |
| 912 | *bytes = current_count; | 905 | *bytes = current_count; |
| 913 | return IPHONE_E_SUCCESS; | 906 | return ret; |
| 914 | } | 907 | } |
| 915 | 908 | ||
| 916 | client->afc_packet->this_length = sizeof(AFCPacket) + 8; | 909 | client->afc_packet->this_length = sizeof(AFCPacket) + 8; |
| @@ -919,7 +912,7 @@ afc_write_file(afc_client_t client, uint64_t handle, | |||
| 919 | out_buffer = (char *) malloc(sizeof(char) * client->afc_packet->entire_length - sizeof(AFCPacket)); | 912 | out_buffer = (char *) malloc(sizeof(char) * client->afc_packet->entire_length - sizeof(AFCPacket)); |
| 920 | memcpy(out_buffer, (char *) &handle, sizeof(uint64_t)); | 913 | memcpy(out_buffer, (char *) &handle, sizeof(uint64_t)); |
| 921 | memcpy(out_buffer + 8, data + current_count, (length - current_count)); | 914 | memcpy(out_buffer + 8, data + current_count, (length - current_count)); |
| 922 | bytes_loc = dispatch_AFC_packet(client, out_buffer, (length - current_count) + 8); | 915 | bytes_loc = afc_dispatch_packet(client, out_buffer, (length - current_count) + 8); |
| 923 | free(out_buffer); | 916 | free(out_buffer); |
| 924 | out_buffer = NULL; | 917 | out_buffer = NULL; |
| 925 | 918 | ||
| @@ -928,7 +921,7 @@ afc_write_file(afc_client_t client, uint64_t handle, | |||
| 928 | if (bytes_loc <= 0) { | 921 | if (bytes_loc <= 0) { |
| 929 | afc_unlock(client); | 922 | afc_unlock(client); |
| 930 | *bytes = current_count; | 923 | *bytes = current_count; |
| 931 | return IPHONE_E_SUCCESS; | 924 | return AFC_E_SUCCESS; |
| 932 | } | 925 | } |
| 933 | 926 | ||
| 934 | zero = bytes_loc; | 927 | zero = bytes_loc; |
| @@ -940,7 +933,7 @@ afc_write_file(afc_client_t client, uint64_t handle, | |||
| 940 | free(acknowledgement); | 933 | free(acknowledgement); |
| 941 | } | 934 | } |
| 942 | *bytes = current_count; | 935 | *bytes = current_count; |
| 943 | return IPHONE_E_SUCCESS; | 936 | return ret; |
| 944 | } | 937 | } |
| 945 | 938 | ||
| 946 | /** Closes a file on the phone. | 939 | /** Closes a file on the phone. |
| @@ -948,12 +941,14 @@ afc_write_file(afc_client_t client, uint64_t handle, | |||
| 948 | * @param client The client to close the file with. | 941 | * @param client The client to close the file with. |
| 949 | * @param handle File handle of a previously opened file. | 942 | * @param handle File handle of a previously opened file. |
| 950 | */ | 943 | */ |
| 951 | iphone_error_t afc_close_file(afc_client_t client, uint64_t handle) | 944 | afc_error_t afc_file_close(afc_client_t client, uint64_t handle) |
| 952 | { | 945 | { |
| 953 | if (!client || (handle == 0)) | ||
| 954 | return IPHONE_E_INVALID_ARG; | ||
| 955 | char *buffer = malloc(sizeof(char) * 8); | 946 | char *buffer = malloc(sizeof(char) * 8); |
| 956 | int bytes = 0; | 947 | int bytes = 0; |
| 948 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 949 | |||
| 950 | if (!client || (handle == 0)) | ||
| 951 | return AFC_E_INVALID_ARGUMENT; | ||
| 957 | 952 | ||
| 958 | afc_lock(client); | 953 | afc_lock(client); |
| 959 | 954 | ||
| @@ -963,13 +958,13 @@ iphone_error_t afc_close_file(afc_client_t client, uint64_t handle) | |||
| 963 | memcpy(buffer, &handle, sizeof(uint64_t)); | 958 | memcpy(buffer, &handle, sizeof(uint64_t)); |
| 964 | client->afc_packet->operation = AFC_OP_FILE_CLOSE; | 959 | client->afc_packet->operation = AFC_OP_FILE_CLOSE; |
| 965 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; | 960 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; |
| 966 | bytes = dispatch_AFC_packet(client, buffer, 8); | 961 | bytes = afc_dispatch_packet(client, buffer, 8); |
| 967 | free(buffer); | 962 | free(buffer); |
| 968 | buffer = NULL; | 963 | buffer = NULL; |
| 969 | 964 | ||
| 970 | if (bytes <= 0) { | 965 | if (bytes <= 0) { |
| 971 | afc_unlock(client); | 966 | afc_unlock(client); |
| 972 | return IPHONE_E_UNKNOWN_ERROR; | 967 | return AFC_E_UNKNOWN_ERROR; |
| 973 | } | 968 | } |
| 974 | 969 | ||
| 975 | // Receive the response | 970 | // Receive the response |
| @@ -978,7 +973,8 @@ iphone_error_t afc_close_file(afc_client_t client, uint64_t handle) | |||
| 978 | free(buffer); | 973 | free(buffer); |
| 979 | 974 | ||
| 980 | afc_unlock(client); | 975 | afc_unlock(client); |
| 981 | return IPHONE_E_SUCCESS; | 976 | |
| 977 | return ret; | ||
| 982 | } | 978 | } |
| 983 | 979 | ||
| 984 | /** Locks or unlocks a file on the phone. | 980 | /** Locks or unlocks a file on the phone. |
| @@ -992,13 +988,15 @@ iphone_error_t afc_close_file(afc_client_t client, uint64_t handle) | |||
| 992 | * AFC_LOCK_SH (shared lock), AFC_LOCK_EX (exclusive lock), | 988 | * AFC_LOCK_SH (shared lock), AFC_LOCK_EX (exclusive lock), |
| 993 | * or AFC_LOCK_UN (unlock). | 989 | * or AFC_LOCK_UN (unlock). |
| 994 | */ | 990 | */ |
| 995 | iphone_error_t afc_lock_file(afc_client_t client, uint64_t handle, afc_lock_op_t operation) | 991 | afc_error_t afc_file_lock(afc_client_t client, uint64_t handle, afc_lock_op_t operation) |
| 996 | { | 992 | { |
| 997 | if (!client || (handle == 0)) | ||
| 998 | return IPHONE_E_INVALID_ARG; | ||
| 999 | char *buffer = malloc(16); | 993 | char *buffer = malloc(16); |
| 1000 | int bytes = 0; | 994 | int bytes = 0; |
| 1001 | uint64_t op = operation; | 995 | uint64_t op = operation; |
| 996 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 997 | |||
| 998 | if (!client || (handle == 0)) | ||
| 999 | return AFC_E_INVALID_ARGUMENT; | ||
| 1002 | 1000 | ||
| 1003 | afc_lock(client); | 1001 | afc_lock(client); |
| 1004 | 1002 | ||
| @@ -1010,14 +1008,14 @@ iphone_error_t afc_lock_file(afc_client_t client, uint64_t handle, afc_lock_op_t | |||
| 1010 | 1008 | ||
| 1011 | client->afc_packet->operation = AFC_OP_FILE_LOCK; | 1009 | client->afc_packet->operation = AFC_OP_FILE_LOCK; |
| 1012 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; | 1010 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; |
| 1013 | bytes = dispatch_AFC_packet(client, buffer, 16); | 1011 | bytes = afc_dispatch_packet(client, buffer, 16); |
| 1014 | free(buffer); | 1012 | free(buffer); |
| 1015 | buffer = NULL; | 1013 | buffer = NULL; |
| 1016 | 1014 | ||
| 1017 | if (bytes <= 0) { | 1015 | if (bytes <= 0) { |
| 1018 | afc_unlock(client); | 1016 | afc_unlock(client); |
| 1019 | log_debug_msg("%s: could not send lock command\n", __func__); | 1017 | log_debug_msg("%s: could not send lock command\n", __func__); |
| 1020 | return IPHONE_E_UNKNOWN_ERROR; | 1018 | return AFC_E_UNKNOWN_ERROR; |
| 1021 | } | 1019 | } |
| 1022 | // Receive the response | 1020 | // Receive the response |
| 1023 | bytes = receive_AFC_data(client, &buffer); | 1021 | bytes = receive_AFC_data(client, &buffer); |
| @@ -1026,10 +1024,8 @@ iphone_error_t afc_lock_file(afc_client_t client, uint64_t handle, afc_lock_op_t | |||
| 1026 | free(buffer); | 1024 | free(buffer); |
| 1027 | } | 1025 | } |
| 1028 | afc_unlock(client); | 1026 | afc_unlock(client); |
| 1029 | if (bytes < 0) { | 1027 | |
| 1030 | return IPHONE_E_AFC_ERROR; | 1028 | return ret; |
| 1031 | } | ||
| 1032 | return IPHONE_E_SUCCESS; | ||
| 1033 | } | 1029 | } |
| 1034 | 1030 | ||
| 1035 | /** Seeks to a given position of a pre-opened file on the phone. | 1031 | /** Seeks to a given position of a pre-opened file on the phone. |
| @@ -1039,13 +1035,17 @@ iphone_error_t afc_lock_file(afc_client_t client, uint64_t handle, afc_lock_op_t | |||
| 1039 | * @param offset Seek offset. | 1035 | * @param offset Seek offset. |
| 1040 | * @param whence Seeking direction, one of SEEK_SET, SEEK_CUR, or SEEK_END. | 1036 | * @param whence Seeking direction, one of SEEK_SET, SEEK_CUR, or SEEK_END. |
| 1041 | * | 1037 | * |
| 1042 | * @return IPHONE_E_SUCCESS on success, IPHONE_E_NOT_ENOUGH_DATA on failure. | 1038 | * @return AFC_E_SUCCESS on success, AFC_E_NOT_ENOUGH_DATA on failure. |
| 1043 | */ | 1039 | */ |
| 1044 | iphone_error_t afc_seek_file(afc_client_t client, uint64_t handle, int64_t offset, int whence) | 1040 | afc_error_t afc_file_seek(afc_client_t client, uint64_t handle, int64_t offset, int whence) |
| 1045 | { | 1041 | { |
| 1046 | char *buffer = (char *) malloc(sizeof(char) * 24); | 1042 | char *buffer = (char *) malloc(sizeof(char) * 24); |
| 1047 | uint32_t zero = 0; | 1043 | uint32_t zero = 0; |
| 1048 | int bytes = 0; | 1044 | int bytes = 0; |
| 1045 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 1046 | |||
| 1047 | if (!client || (handle == 0)) | ||
| 1048 | return AFC_E_INVALID_ARGUMENT; | ||
| 1049 | 1049 | ||
| 1050 | afc_lock(client); | 1050 | afc_lock(client); |
| 1051 | 1051 | ||
| @@ -1056,13 +1056,13 @@ iphone_error_t afc_seek_file(afc_client_t client, uint64_t handle, int64_t offse | |||
| 1056 | memcpy(buffer + 16, &offset, sizeof(uint64_t)); // offset | 1056 | memcpy(buffer + 16, &offset, sizeof(uint64_t)); // offset |
| 1057 | client->afc_packet->operation = AFC_OP_FILE_SEEK; | 1057 | client->afc_packet->operation = AFC_OP_FILE_SEEK; |
| 1058 | client->afc_packet->this_length = client->afc_packet->entire_length = 0; | 1058 | client->afc_packet->this_length = client->afc_packet->entire_length = 0; |
| 1059 | bytes = dispatch_AFC_packet(client, buffer, 24); | 1059 | bytes = afc_dispatch_packet(client, buffer, 24); |
| 1060 | free(buffer); | 1060 | free(buffer); |
| 1061 | buffer = NULL; | 1061 | buffer = NULL; |
| 1062 | 1062 | ||
| 1063 | if (bytes <= 0) { | 1063 | if (bytes <= 0) { |
| 1064 | afc_unlock(client); | 1064 | afc_unlock(client); |
| 1065 | return IPHONE_E_NOT_ENOUGH_DATA; | 1065 | return AFC_E_NOT_ENOUGH_DATA; |
| 1066 | } | 1066 | } |
| 1067 | // Receive response | 1067 | // Receive response |
| 1068 | bytes = receive_AFC_data(client, &buffer); | 1068 | bytes = receive_AFC_data(client, &buffer); |
| @@ -1088,10 +1088,14 @@ iphone_error_t afc_seek_file(afc_client_t client, uint64_t handle, int64_t offse | |||
| 1088 | * @note This function is more akin to ftruncate than truncate, and truncate | 1088 | * @note This function is more akin to ftruncate than truncate, and truncate |
| 1089 | * calls would have to open the file before calling this, sadly. | 1089 | * calls would have to open the file before calling this, sadly. |
| 1090 | */ | 1090 | */ |
| 1091 | iphone_error_t afc_truncate_file(afc_client_t client, uint64_t handle, uint64_t newsize) | 1091 | afc_error_t afc_file_truncate(afc_client_t client, uint64_t handle, uint64_t newsize) |
| 1092 | { | 1092 | { |
| 1093 | char *buffer = (char *) malloc(sizeof(char) * 16); | 1093 | char *buffer = (char *) malloc(sizeof(char) * 16); |
| 1094 | int bytes = 0; | 1094 | int bytes = 0; |
| 1095 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 1096 | |||
| 1097 | if (!client || (handle == 0)) | ||
| 1098 | return AFC_E_INVALID_ARGUMENT; | ||
| 1095 | 1099 | ||
| 1096 | afc_lock(client); | 1100 | afc_lock(client); |
| 1097 | 1101 | ||
| @@ -1100,13 +1104,13 @@ iphone_error_t afc_truncate_file(afc_client_t client, uint64_t handle, uint64_t | |||
| 1100 | memcpy(buffer + 8, &newsize, sizeof(uint64_t)); // newsize | 1104 | memcpy(buffer + 8, &newsize, sizeof(uint64_t)); // newsize |
| 1101 | client->afc_packet->operation = AFC_OP_FILE_SET_SIZE; | 1105 | client->afc_packet->operation = AFC_OP_FILE_SET_SIZE; |
| 1102 | client->afc_packet->this_length = client->afc_packet->entire_length = 0; | 1106 | client->afc_packet->this_length = client->afc_packet->entire_length = 0; |
| 1103 | bytes = dispatch_AFC_packet(client, buffer, 16); | 1107 | bytes = afc_dispatch_packet(client, buffer, 16); |
| 1104 | free(buffer); | 1108 | free(buffer); |
| 1105 | buffer = NULL; | 1109 | buffer = NULL; |
| 1106 | 1110 | ||
| 1107 | if (bytes <= 0) { | 1111 | if (bytes <= 0) { |
| 1108 | afc_unlock(client); | 1112 | afc_unlock(client); |
| 1109 | return IPHONE_E_NOT_ENOUGH_DATA; | 1113 | return AFC_E_NOT_ENOUGH_DATA; |
| 1110 | } | 1114 | } |
| 1111 | // Receive response | 1115 | // Receive response |
| 1112 | bytes = receive_AFC_data(client, &buffer); | 1116 | bytes = receive_AFC_data(client, &buffer); |
| @@ -1115,10 +1119,7 @@ iphone_error_t afc_truncate_file(afc_client_t client, uint64_t handle, uint64_t | |||
| 1115 | 1119 | ||
| 1116 | afc_unlock(client); | 1120 | afc_unlock(client); |
| 1117 | 1121 | ||
| 1118 | if (bytes < 0) { | 1122 | return ret; |
| 1119 | return IPHONE_E_AFC_ERROR; | ||
| 1120 | } | ||
| 1121 | return IPHONE_E_SUCCESS; | ||
| 1122 | } | 1123 | } |
| 1123 | 1124 | ||
| 1124 | /** Sets the size of a file on the phone without prior opening it. | 1125 | /** Sets the size of a file on the phone without prior opening it. |
| @@ -1127,18 +1128,19 @@ iphone_error_t afc_truncate_file(afc_client_t client, uint64_t handle, uint64_t | |||
| 1127 | * @param path The path of the file to be truncated. | 1128 | * @param path The path of the file to be truncated. |
| 1128 | * @param newsize The size to set the file to. | 1129 | * @param newsize The size to set the file to. |
| 1129 | * | 1130 | * |
| 1130 | * @return IPHONE_E_SUCCESS if everything went well, IPHONE_E_INVALID_ARG | 1131 | * @return AFC_E_SUCCESS if everything went well, AFC_E_INVALID_ARGUMENT |
| 1131 | * if arguments are NULL or invalid, IPHONE_E_NOT_ENOUGH_DATA otherwise. | 1132 | * if arguments are NULL or invalid, AFC_E_NOT_ENOUGH_DATA otherwise. |
| 1132 | */ | 1133 | */ |
| 1133 | iphone_error_t afc_truncate(afc_client_t client, const char *path, off_t newsize) | 1134 | afc_error_t afc_truncate(afc_client_t client, const char *path, off_t newsize) |
| 1134 | { | 1135 | { |
| 1135 | char *response = NULL; | 1136 | char *response = NULL; |
| 1136 | char *send = (char *) malloc(sizeof(char) * (strlen(path) + 1 + 8)); | 1137 | char *send = (char *) malloc(sizeof(char) * (strlen(path) + 1 + 8)); |
| 1137 | int bytes = 0; | 1138 | int bytes = 0; |
| 1138 | uint64_t size_requested = newsize; | 1139 | uint64_t size_requested = newsize; |
| 1140 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 1139 | 1141 | ||
| 1140 | if (!client || !path || !client->afc_packet || client->sfd < 0) | 1142 | if (!client || !path || !client->afc_packet || client->sfd < 0) |
| 1141 | return IPHONE_E_INVALID_ARG; | 1143 | return AFC_E_INVALID_ARGUMENT; |
| 1142 | 1144 | ||
| 1143 | afc_lock(client); | 1145 | afc_lock(client); |
| 1144 | 1146 | ||
| @@ -1147,11 +1149,11 @@ iphone_error_t afc_truncate(afc_client_t client, const char *path, off_t newsize | |||
| 1147 | memcpy(send + 8, path, strlen(path) + 1); | 1149 | memcpy(send + 8, path, strlen(path) + 1); |
| 1148 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; | 1150 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; |
| 1149 | client->afc_packet->operation = AFC_OP_TRUNCATE; | 1151 | client->afc_packet->operation = AFC_OP_TRUNCATE; |
| 1150 | bytes = dispatch_AFC_packet(client, send, 8 + strlen(path) + 1); | 1152 | bytes = afc_dispatch_packet(client, send, 8 + strlen(path) + 1); |
| 1151 | free(send); | 1153 | free(send); |
| 1152 | if (bytes <= 0) { | 1154 | if (bytes <= 0) { |
| 1153 | afc_unlock(client); | 1155 | afc_unlock(client); |
| 1154 | return IPHONE_E_NOT_ENOUGH_DATA; | 1156 | return AFC_E_NOT_ENOUGH_DATA; |
| 1155 | } | 1157 | } |
| 1156 | // Receive response | 1158 | // Receive response |
| 1157 | bytes = receive_AFC_data(client, &response); | 1159 | bytes = receive_AFC_data(client, &response); |
| @@ -1160,10 +1162,7 @@ iphone_error_t afc_truncate(afc_client_t client, const char *path, off_t newsize | |||
| 1160 | 1162 | ||
| 1161 | afc_unlock(client); | 1163 | afc_unlock(client); |
| 1162 | 1164 | ||
| 1163 | if (bytes < 0) { | 1165 | return ret; |
| 1164 | return IPHONE_E_AFC_ERROR; | ||
| 1165 | } | ||
| 1166 | return IPHONE_E_SUCCESS; | ||
| 1167 | } | 1166 | } |
| 1168 | 1167 | ||
| 1169 | /** Creates a hard link or symbolic link on the device. | 1168 | /** Creates a hard link or symbolic link on the device. |
| @@ -1173,18 +1172,19 @@ iphone_error_t afc_truncate(afc_client_t client, const char *path, off_t newsize | |||
| 1173 | * @param target The file to be linked. | 1172 | * @param target The file to be linked. |
| 1174 | * @param linkname The name of link. | 1173 | * @param linkname The name of link. |
| 1175 | * | 1174 | * |
| 1176 | * @return IPHONE_E_SUCCESS if everything went well, IPHONE_E_INVALID_ARG | 1175 | * @return AFC_E_SUCCESS if everything went well, AFC_E_INVALID_ARGUMENT |
| 1177 | * if arguments are NULL or invalid, IPHONE_E_NOT_ENOUGH_DATA otherwise. | 1176 | * if arguments are NULL or invalid, AFC_E_NOT_ENOUGH_DATA otherwise. |
| 1178 | */ | 1177 | */ |
| 1179 | iphone_error_t afc_make_link(afc_client_t client, afc_link_type_t linktype, const char *target, const char *linkname) | 1178 | afc_error_t afc_make_link(afc_client_t client, afc_link_type_t linktype, const char *target, const char *linkname) |
| 1180 | { | 1179 | { |
| 1181 | char *response = NULL; | 1180 | char *response = NULL; |
| 1182 | char *send = (char *) malloc(sizeof(char) * (strlen(target)+1 + strlen(linkname)+1 + 8)); | 1181 | char *send = (char *) malloc(sizeof(char) * (strlen(target)+1 + strlen(linkname)+1 + 8)); |
| 1183 | int bytes = 0; | 1182 | int bytes = 0; |
| 1184 | uint64_t type = linktype; | 1183 | uint64_t type = linktype; |
| 1184 | afc_error_t ret = AFC_E_UNKNOWN_ERROR; | ||
| 1185 | 1185 | ||
| 1186 | if (!client || !target || !linkname || !client->afc_packet || client->sfd < 0) | 1186 | if (!client || !target || !linkname || !client->afc_packet || client->sfd < 0) |
| 1187 | return IPHONE_E_INVALID_ARG; | 1187 | return AFC_E_INVALID_ARGUMENT; |
| 1188 | 1188 | ||
| 1189 | afc_lock(client); | 1189 | afc_lock(client); |
| 1190 | 1190 | ||
| @@ -1198,11 +1198,11 @@ iphone_error_t afc_make_link(afc_client_t client, afc_link_type_t linktype, cons | |||
| 1198 | memcpy(send + 8 + strlen(target) + 1, linkname, strlen(linkname) + 1); | 1198 | memcpy(send + 8 + strlen(target) + 1, linkname, strlen(linkname) + 1); |
| 1199 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; | 1199 | client->afc_packet->entire_length = client->afc_packet->this_length = 0; |
| 1200 | client->afc_packet->operation = AFC_OP_MAKE_LINK; | 1200 | client->afc_packet->operation = AFC_OP_MAKE_LINK; |
| 1201 | bytes = dispatch_AFC_packet(client, send, 8 + strlen(linkname) + 1 + strlen(target) + 1); | 1201 | bytes = afc_dispatch_packet(client, send, 8 + strlen(linkname) + 1 + strlen(target) + 1); |
| 1202 | free(send); | 1202 | free(send); |
| 1203 | if (bytes <= 0) { | 1203 | if (bytes <= 0) { |
| 1204 | afc_unlock(client); | 1204 | afc_unlock(client); |
| 1205 | return IPHONE_E_NOT_ENOUGH_DATA; | 1205 | return AFC_E_NOT_ENOUGH_DATA; |
| 1206 | } | 1206 | } |
| 1207 | // Receive response | 1207 | // Receive response |
| 1208 | bytes = receive_AFC_data(client, &response); | 1208 | bytes = receive_AFC_data(client, &response); |
| @@ -1211,9 +1211,5 @@ iphone_error_t afc_make_link(afc_client_t client, afc_link_type_t linktype, cons | |||
| 1211 | 1211 | ||
| 1212 | afc_unlock(client); | 1212 | afc_unlock(client); |
| 1213 | 1213 | ||
| 1214 | if (bytes < 0) { | 1214 | return ret; |
| 1215 | return IPHONE_E_NOT_ENOUGH_DATA; | ||
| 1216 | } else { | ||
| 1217 | return IPHONE_E_SUCCESS; | ||
| 1218 | } | ||
| 1219 | } | 1215 | } |
| @@ -26,6 +26,8 @@ | |||
| 26 | #include <glib.h> | 26 | #include <glib.h> |
| 27 | #include <stdint.h> | 27 | #include <stdint.h> |
| 28 | 28 | ||
| 29 | #include "libiphone/afc.h" | ||
| 30 | |||
| 29 | #define AFC_MAGIC "CFA6LPAA" | 31 | #define AFC_MAGIC "CFA6LPAA" |
| 30 | #define AFC_MAGIC_LEN (8) | 32 | #define AFC_MAGIC_LEN (8) |
| 31 | 33 | ||
