summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorGravatar Nikias Bassen2022-06-20 14:14:43 +0200
committerGravatar Nikias Bassen2022-06-20 14:14:43 +0200
commitaa25a29e1cf7bc81450a85fdc3320c48c2d95afb (patch)
treef35ca55518affa72cf50e26ae032d3fb4da79ff8
parentf6c3d53006733e1f5bae4b073d4e7f19cefd0870 (diff)
downloadidevicerestore-aa25a29e1cf7bc81450a85fdc3320c48c2d95afb.tar.gz
idevicerestore-aa25a29e1cf7bc81450a85fdc3320c48c2d95afb.tar.bz2
Remove more serial number checks, and get ECID early on in all modes
Some devices seem to not have a serial number, usually in restore mode, which will cause the restore operation to fail since we specifically check for it. An earlier commit already removed the actual comparison in favor of comparing the ECID, but some checks would still result in restore failures as it can't retrieve the serial number on said devices at all. This commit also makes sure to get the ECID in all modes as early as possible and removes all the helper functions for it since they are not needed anymore.
-rw-r--r--src/dfu.c43
-rw-r--r--src/dfu.h1
-rw-r--r--src/idevicerestore.c58
-rw-r--r--src/normal.c20
-rw-r--r--src/normal.h1
-rw-r--r--src/recovery.c18
-rw-r--r--src/recovery.h1
-rw-r--r--src/restore.c24
8 files changed, 31 insertions, 135 deletions
diff --git a/src/dfu.c b/src/dfu.c
index fc2622e..cb4d2b3 100644
--- a/src/dfu.c
+++ b/src/dfu.c
@@ -42,8 +42,6 @@ static int dfu_progress_callback(irecv_client_t client, const irecv_event_t* eve
int dfu_client_new(struct idevicerestore_client_t* client)
{
- int i = 0;
- int attempts = 10;
irecv_client_t dfu = NULL;
if (client->dfu == NULL) {
@@ -55,18 +53,9 @@ int dfu_client_new(struct idevicerestore_client_t* client)
}
}
- for (i = 1; i <= attempts; i++) {
- if (irecv_open_with_ecid(&dfu, client->ecid) == IRECV_E_SUCCESS) {
- break;
- }
-
- if (i >= attempts) {
- error("ERROR: Unable to connect to device in DFU mode\n");
- return -1;
- }
-
- sleep(1);
- debug("Retrying connection...\n");
+ if (irecv_open_with_ecid_and_attempts(&dfu, client->ecid, 10) != IRECV_E_SUCCESS) {
+ error("ERROR: Unable to connect to device in DFU mode\n");
+ return -1;
}
irecv_event_subscribe(dfu, IRECV_PROGRESS, &dfu_progress_callback, NULL);
@@ -95,11 +84,17 @@ irecv_device_t dfu_get_irecv_device(struct idevicerestore_client_t* client)
irecv_device_t device = NULL;
irecv_init();
- if (irecv_open_with_ecid(&dfu, client->ecid) != IRECV_E_SUCCESS) {
+ if (irecv_open_with_ecid_and_attempts(&dfu, client->ecid, 10) != IRECV_E_SUCCESS) {
return NULL;
}
dfu_error = irecv_devices_get_device_by_client(dfu, &device);
+ if (dfu_error == IRECV_E_SUCCESS) {
+ if (client->ecid == 0) {
+ const struct irecv_device_info *device_info = irecv_get_device_info(dfu);
+ client->ecid = device_info->ecid;
+ }
+ }
irecv_close(dfu);
if (dfu_error != IRECV_E_SUCCESS) {
return NULL;
@@ -227,24 +222,6 @@ int dfu_get_cpid(struct idevicerestore_client_t* client, unsigned int* cpid)
return 0;
}
-int dfu_get_ecid(struct idevicerestore_client_t* client, uint64_t* ecid)
-{
- if(client->dfu == NULL) {
- if (dfu_client_new(client) < 0) {
- return -1;
- }
- }
-
- const struct irecv_device_info *device_info = irecv_get_device_info(client->dfu->client);
- if (!device_info) {
- return -1;
- }
-
- *ecid = device_info->ecid;
-
- return 0;
-}
-
int dfu_is_image4_supported(struct idevicerestore_client_t* client)
{
if(client->dfu == NULL) {
diff --git a/src/dfu.h b/src/dfu.h
index f501531..6712442 100644
--- a/src/dfu.h
+++ b/src/dfu.h
@@ -43,7 +43,6 @@ irecv_device_t dfu_get_irecv_device(struct idevicerestore_client_t* client);
int dfu_send_buffer(struct idevicerestore_client_t* client, unsigned char* buffer, unsigned int size);
int dfu_send_component(struct idevicerestore_client_t* client, plist_t build_identity, const char* component);
int dfu_get_cpid(struct idevicerestore_client_t* client, unsigned int* cpid);
-int dfu_get_ecid(struct idevicerestore_client_t* client, uint64_t* ecid);
int dfu_is_image4_supported(struct idevicerestore_client_t* client);
int dfu_get_ap_nonce(struct idevicerestore_client_t* client, unsigned char** nonce, int* nonce_size);
int dfu_get_sep_nonce(struct idevicerestore_client_t* client, unsigned char** nonce, int* nonce_size);
diff --git a/src/idevicerestore.c b/src/idevicerestore.c
index 349e03e..51e7ce1 100644
--- a/src/idevicerestore.c
+++ b/src/idevicerestore.c
@@ -453,6 +453,12 @@ int idevicerestore_start(struct idevicerestore_client_t* client)
error("ERROR: Unable to discover device type\n");
return -1;
}
+ if (client->ecid == 0) {
+ error("ERROR: Unable to determine ECID\n");
+ return -1;
+ }
+ info("ECID: %" PRIu64 "\n", client->ecid);
+
idevicerestore_progress(client, RESTORE_STEP_DETECT, 0.2);
info("Identified device as %s, %s\n", client->device->hardware_model, client->device->product_type);
@@ -1037,13 +1043,6 @@ int idevicerestore_start(struct idevicerestore_client_t* client)
/* retrieve shsh blobs if required */
if (tss_enabled) {
int stashbag_commit_required = 0;
- debug("Getting device's ECID for TSS request\n");
- /* fetch the device's ECID for the TSS request */
- if (get_ecid(client, &client->ecid) < 0) {
- error("ERROR: Unable to find device ECID\n");
- return -1;
- }
- info("Found ECID %" PRIu64 "\n", client->ecid);
if (client->mode == MODE_NORMAL && !(client->flags & FLAG_ERASE) && !(client->flags & FLAG_SHSHONLY)) {
plist_t node = normal_get_lockdown_value(client, NULL, "HasSiDP");
@@ -1348,12 +1347,6 @@ int idevicerestore_start(struct idevicerestore_client_t* client)
// now finally do the magic to put the device into restore mode
if (client->mode == MODE_RECOVERY) {
- if (client->srnm == NULL) {
- error("ERROR: could not retrieve device serial number. Can't continue.\n");
- if (delete_fs && filesystem)
- unlink(filesystem);
- return -1;
- }
if (recovery_enter_restore(client, build_identity) < 0) {
error("ERROR: Unable to place device into restore mode\n");
if (client->tss)
@@ -1826,45 +1819,6 @@ int is_image4_supported(struct idevicerestore_client_t* client)
return res;
}
-int get_ecid(struct idevicerestore_client_t* client, uint64_t* ecid)
-{
- int mode = _MODE_UNKNOWN;
-
- if (client->mode) {
- mode = client->mode->index;
- }
-
- switch (mode) {
- case _MODE_NORMAL:
- if (normal_get_ecid(client, ecid) < 0) {
- *ecid = 0;
- return -1;
- }
- break;
-
- case _MODE_DFU:
- if (dfu_get_ecid(client, ecid) < 0) {
- *ecid = 0;
- return -1;
- }
- break;
-
- case _MODE_RECOVERY:
- if (recovery_get_ecid(client, ecid) < 0) {
- *ecid = 0;
- return -1;
- }
- break;
-
- default:
- error("ERROR: Device is in an invalid state\n");
- *ecid = 0;
- return -1;
- }
-
- return 0;
-}
-
int get_ap_nonce(struct idevicerestore_client_t* client, unsigned char** nonce, int* nonce_size)
{
int mode = _MODE_UNKNOWN;
diff --git a/src/normal.c b/src/normal.c
index 89f713b..7f570da 100644
--- a/src/normal.c
+++ b/src/normal.c
@@ -41,6 +41,7 @@ static int normal_idevice_new(struct idevicerestore_client_t* client, idevice_t*
idevice_t dev = NULL;
idevice_error_t device_error;
lockdownd_client_t lockdown = NULL;
+ plist_t node = NULL;
*device = NULL;
@@ -65,6 +66,10 @@ static int normal_idevice_new(struct idevicerestore_client_t* client, idevice_t*
return -1;
}
free(type);
+ if (lockdownd_get_value(lockdown, NULL, "UniqueChipID", &node) == LOCKDOWN_E_SUCCESS) {
+ plist_get_uint_val(node, &client->ecid);
+ plist_free(node);
+ }
lockdownd_client_free(lockdown);
lockdown = NULL;
@@ -107,7 +112,7 @@ static int normal_idevice_new(struct idevicerestore_client_t* client, idevice_t*
}
free(type);
- plist_t node = NULL;
+ node = NULL;
if ((lockdownd_get_value(lockdown, NULL, "UniqueChipID", &node) != LOCKDOWN_E_SUCCESS) || !node || (plist_get_node_type(node) != PLIST_UINT)){
if (node) {
plist_free(node);
@@ -362,19 +367,6 @@ int normal_is_image4_supported(struct idevicerestore_client_t* client)
return bval;
}
-int normal_get_ecid(struct idevicerestore_client_t* client, uint64_t* ecid)
-{
- plist_t unique_chip_node = normal_get_lockdown_value(client, NULL, "UniqueChipID");
- if (!unique_chip_node || plist_get_node_type(unique_chip_node) != PLIST_UINT) {
- error("ERROR: Unable to get ECID\n");
- return -1;
- }
- plist_get_uint_val(unique_chip_node, ecid);
- plist_free(unique_chip_node);
-
- return 0;
-}
-
int normal_get_preflight_info(struct idevicerestore_client_t* client, plist_t *preflight_info)
{
uint8_t has_telephony_capability = 0;
diff --git a/src/normal.h b/src/normal.h
index f438f9b..85464db 100644
--- a/src/normal.h
+++ b/src/normal.h
@@ -35,7 +35,6 @@ extern "C" {
int normal_check_mode(struct idevicerestore_client_t* client);
irecv_device_t normal_get_irecv_device(struct idevicerestore_client_t* client);
int normal_enter_recovery(struct idevicerestore_client_t* client);
-int normal_get_ecid(struct idevicerestore_client_t* client, uint64_t* ecid);
int normal_is_image4_supported(struct idevicerestore_client_t* client);
int normal_get_ap_nonce(struct idevicerestore_client_t* client, unsigned char** nonce, int* nonce_size);
int normal_get_sep_nonce(struct idevicerestore_client_t* client, unsigned char** nonce, int* nonce_size);
diff --git a/src/recovery.c b/src/recovery.c
index bcdd945..1a9c970 100644
--- a/src/recovery.c
+++ b/src/recovery.c
@@ -507,24 +507,6 @@ int recovery_send_kernelcache(struct idevicerestore_client_t* client, plist_t bu
return 0;
}
-int recovery_get_ecid(struct idevicerestore_client_t* client, uint64_t* ecid)
-{
- if(client->recovery == NULL) {
- if (recovery_client_new(client) < 0) {
- return -1;
- }
- }
-
- const struct irecv_device_info *device_info = irecv_get_device_info(client->recovery->client);
- if (!device_info) {
- return -1;
- }
-
- *ecid = device_info->ecid;
-
- return 0;
-}
-
int recovery_is_image4_supported(struct idevicerestore_client_t* client)
{
if(client->recovery == NULL) {
diff --git a/src/recovery.h b/src/recovery.h
index 154d7d1..92214af 100644
--- a/src/recovery.h
+++ b/src/recovery.h
@@ -54,7 +54,6 @@ int recovery_send_loaded_by_iboot(struct idevicerestore_client_t* client, plist_
int recovery_send_reset(struct idevicerestore_client_t* client);
int recovery_send_ticket(struct idevicerestore_client_t* client);
int recovery_set_autoboot(struct idevicerestore_client_t* client, int enable);
-int recovery_get_ecid(struct idevicerestore_client_t* client, uint64_t* ecid);
int recovery_is_image4_supported(struct idevicerestore_client_t* client);
int recovery_get_ap_nonce(struct idevicerestore_client_t* client, unsigned char** nonce, int* nonce_size);
int recovery_get_sep_nonce(struct idevicerestore_client_t* client, unsigned char** nonce, int* nonce_size);
diff --git a/src/restore.c b/src/restore.c
index 76194bf..c58f46a 100644
--- a/src/restore.c
+++ b/src/restore.c
@@ -278,18 +278,12 @@ irecv_device_t restore_get_irecv_device(struct idevicerestore_client_t* client)
}
if (client->srnm == NULL) {
- restore_error = restored_get_value(restore, "SerialNumber", &node);
- if (restore_error != RESTORE_E_SUCCESS || !node || plist_get_node_type(node) != PLIST_STRING) {
- error("ERROR: Unable to get SerialNumber from restored\n");
- restored_client_free(restore);
- idevice_free(device);
- return NULL;
+ if (restored_get_value(restore, "SerialNumber", &node) == RESTORE_E_SUCCESS) {
+ plist_get_string_val(node, &client->srnm);
+ info("INFO: device serial number is %s\n", client->srnm);
+ plist_free(node);
+ node = NULL;
}
-
- plist_get_string_val(node, &client->srnm);
- info("INFO: device serial number is %s\n", client->srnm);
- plist_free(node);
- node = NULL;
}
restore_error = restored_get_value(restore, "HardwareModel", &node);
@@ -450,17 +444,17 @@ int restore_open_with_timeout(struct idevicerestore_client_t* client)
restored_error_t restore_error = RESTORE_E_SUCCESS;
// no context exists so bail
- if(client == NULL) {
+ if (client == NULL) {
return -1;
}
- if(client->srnm == NULL) {
- error("ERROR: no SerialNumber in client data!\n");
+ if (client->ecid == 0) {
+ error("ERROR: no ECID in client data!\n");
return -1;
}
// create our restore client if it doesn't yet exist
- if(client->restore == NULL) {
+ if (client->restore == NULL) {
client->restore = (struct restore_client_t*) malloc(sizeof(struct restore_client_t));
if(client->restore == NULL) {
error("ERROR: Out of memory\n");