diff options
Diffstat (limited to 'src/idevicerestore.c')
-rw-r--r-- | src/idevicerestore.c | 46 |
1 files changed, 45 insertions, 1 deletions
diff --git a/src/idevicerestore.c b/src/idevicerestore.c index f1d441a..ca3c94c 100644 --- a/src/idevicerestore.c +++ b/src/idevicerestore.c @@ -49,6 +49,7 @@ static struct option longopts[] = { { "custom", no_argument, NULL, 'c' }, { "cydia", no_argument, NULL, 's' }, { "exclude", no_argument, NULL, 'x' }, + { "shsh", no_argument, NULL, 't' }, { NULL, 0, NULL, 0 } }; @@ -63,6 +64,7 @@ void usage(int argc, char* argv[]) { printf(" -c, --custom\t\trestore with a custom firmware\n"); printf(" -s, --cydia\t\tuse Cydia's signature service instead of Apple's\n"); printf(" -x, --exclude\t\texclude nor/baseband upgrade\n"); + printf(" -t, --shsh\t\tfetch TSS record and save to .shsh file, then exit\n"); printf("\n"); } @@ -72,6 +74,8 @@ int main(int argc, char* argv[]) { char* ipsw = NULL; char* uuid = NULL; int tss_enabled = 0; + int shsh_only = 0; + char* shsh_dir = NULL; use_apple_server=1; // create an instance of our context @@ -82,7 +86,7 @@ int main(int argc, char* argv[]) { } memset(client, '\0', sizeof(struct idevicerestore_client_t)); - while ((opt = getopt_long(argc, argv, "dhcesxu:", longopts, &optindex)) > 0) { + while ((opt = getopt_long(argc, argv, "dhcesxtu:", longopts, &optindex)) > 0) { switch (opt) { case 'h': usage(argc, argv); @@ -112,6 +116,10 @@ int main(int argc, char* argv[]) { uuid = optarg; break; + case 't': + shsh_only = 1; + break; + default: usage(argc, argv); return -1; @@ -372,6 +380,42 @@ int main(int argc, char* argv[]) { } } + if (shsh_only) { + if (!tss_enabled) { + info("This device does not require a TSS record"); + return 0; + } + if (!client->tss) { + error("ERROR: could not fetch TSS record"); + plist_free(buildmanifest); + return -1; + } else { + char *bin = NULL; + uint32_t blen = 0; + plist_to_bin(client->tss, &bin, &blen); + if (bin) { + char zfn[512]; + sprintf(zfn, "shsh/%lld-%s-%s.shsh", (long long int)client->ecid, client->device->product, client->version); + mkdir("shsh", 0755); + struct stat fst; + if (stat(zfn, &fst) != 0) { + gzFile zf = gzopen(zfn, "wb"); + gzwrite(zf, bin, blen); + gzclose(zf); + info("SHSH saved to '%s'\n", zfn); + } else { + info("SHSH '%s' already present.\n", zfn); + } + free(bin); + } else { + error("ERROR: could not get TSS record data\n"); + } + plist_free(client->tss); + plist_free(buildmanifest); + return 0; + } + } + /* verify if we have tss records if required */ if ((tss_enabled) && (client->tss == NULL)) { error("ERROR: Unable to proceed without a TSS record.\n"); |