Esempio n. 1
0
void writeImg3Element(AbstractFile* file, Img3Element* element, Img3Info* info) {
	off_t curPos;

	if(info->exploit24k && element->header->magic == IMG3_TYPE_MAGIC) {
		// Drop TYPE tag for exploited LLB, because it throws off our payload calculations
		// Bootrom shouldn't care anyway, and kernel currently doesn't care
		return;
	}

	curPos = file->tell(file);

	if(element->header->magic == IMG3_CERT_MAGIC) {
		if(info->exploit24k) {
			do24kpwn(info, element, curPos, x24kpwn_overflow_data, sizeof(x24kpwn_overflow_data), x24kpwn_payload_data, sizeof(x24kpwn_payload_data));
		} else if(info->exploitN8824k) {
			do24kpwn(info, element, curPos, n8824kpwn_overflow_data, sizeof(n8824kpwn_overflow_data), n8824kpwn_payload_data, sizeof(n8824kpwn_payload_data));
		}
	}

	flipAppleImg3Header(element->header);
	file->write(file, element->header, sizeof(AppleImg3Header));
	flipAppleImg3Header(element->header);

	element->write(file, element, info);

	file->seek(file, curPos + element->header->size);
}
Esempio n. 2
0
void writeImg3Element(AbstractFile* file, Img3Element* element, Img3Info* info) {
	off_t curPos;

	curPos = file->tell(file);

	flipAppleImg3Header(element->header);
	file->write(file, element->header, sizeof(AppleImg3Header));
	flipAppleImg3Header(element->header);

	element->write(file, element, info);

	file->seek(file, curPos + element->header->size);
}
Esempio n. 3
0
File: img3.c Progetto: 0x76/opensn0w
void writeImg3Root(AbstractFile * file, Img3Element * element, Img3Info * info)
{
	AppleImg3RootHeader *header;
	Img3Element *current;
	off_t curPos;

	curPos = file->tell(file);
	curPos -= sizeof(AppleImg3Header);

	file->seek(file, curPos + sizeof(AppleImg3RootHeader));

	header = (AppleImg3RootHeader *) element->header;

	current = (Img3Element *) element->data;
	while (current != NULL) {
		if (current->header->magic == IMG3_SHSH_MAGIC) {
			header->extra.shshOffset =
			    (uint32_t) (file->tell(file) -
					sizeof(AppleImg3RootHeader));
		}

		if (current->header->magic != IMG3_KBAG_MAGIC
		    || info->encrypted) {
			writeImg3Element(file, current, info);
		}

		current = current->next;
	}

	header->base.dataSize =
	    file->tell(file) - (curPos + sizeof(AppleImg3RootHeader));
	header->base.size = sizeof(AppleImg3RootHeader) + header->base.dataSize;

	file->seek(file, curPos);

	flipAppleImg3Header(&(header->base));
	flipAppleImg3RootExtra(&(header->extra));
	file->write(file, header, sizeof(AppleImg3RootHeader));
	flipAppleImg3RootExtra(&(header->extra));
	flipAppleImg3Header(&(header->base));

	file->seek(file, header->base.size);
}
Esempio n. 4
0
File: img3.c Progetto: 0x76/opensn0w
Img3Element *readImg3Element(AbstractFile * file)
{
	Img3Element *toReturn;
	AppleImg3Header *header;
	off_t curPos;

	curPos = file->tell(file);

	header = (AppleImg3Header *) malloc(sizeof(AppleImg3Header));
	file->read(file, header, sizeof(AppleImg3Header));
	flipAppleImg3Header(header);

	toReturn = (Img3Element *) malloc(sizeof(Img3Element));
	toReturn->header = header;
	toReturn->next = NULL;

	switch (header->magic) {
	case IMG3_MAGIC:
		readImg3Root(file, toReturn);
		break;

	case IMG3_KBAG_MAGIC:
		toReturn->data = (unsigned char *)malloc(header->dataSize);
		toReturn->write = writeImg3KBAG;
		toReturn->free = freeImg3Default;
		file->read(file, toReturn->data, header->dataSize);
		flipAppleImg3KBAGHeader((AppleImg3KBAGHeader *) toReturn->data);
		break;

	default:
		{
			uint32_t sz = header->size - sizeof(AppleImg3Header);	/* header->dataSize */
			toReturn->data = (unsigned char *)malloc(sz);
			toReturn->write = writeImg3Default;
			toReturn->free = freeImg3Default;
			file->read(file, toReturn->data, sz);
		}
	}

	file->seek(file, curPos + toReturn->header->size);

	return toReturn;
}
Esempio n. 5
0
static int
cryptoMagic(X509 *x0, X509 *x1, X509 *x2,
	    const unsigned char *toHashData, int toHashLength,
	    /*XXX const*/ unsigned char *rsaSigData, int rsaSigLen,
	    DataValue *partialDigest)
{
	int rv = 0;
	EVP_PKEY *pk = X509_get_pubkey(x2);
	if (pk) {
		if (pk->type == EVP_PKEY_RSA) {
			RSA *rsa = EVP_PKEY_get1_RSA(pk);
			if (rsa) {
				X509_STORE *store = X509_STORE_new();
				if (store) {
					X509_STORE_CTX ctx;
					X509_STORE_add_cert(store, x0);
					X509_STORE_add_cert(store, x1);
					if (X509_STORE_CTX_init(&ctx, store, x2, 0) == 1) {
						X509_STORE_CTX_set_flags(&ctx, X509_V_FLAG_IGNORE_CRITICAL);
						if (X509_verify_cert(&ctx) == 1) {
							unsigned char md[SHA_DIGEST_LENGTH];
							if (partialDigest) {
								// XXX we need to flip ECID back before hashing
								flipAppleImg3Header((AppleImg3Header *)toHashData);
								doPartialSHA1(md, toHashData, toHashLength, partialDigest);
							} else {
								SHA1(toHashData, toHashLength, md);
							}
							rv = RSA_verify(NID_sha1, md, SHA_DIGEST_LENGTH, rsaSigData, rsaSigLen, rsa);
						}
						X509_STORE_CTX_cleanup(&ctx);
					}
					X509_STORE_free(store);
				}
				RSA_free(rsa);
			}
		}
		EVP_PKEY_free(pk);
	}
	return rv ? 0 : -1;
}
Esempio n. 6
0
static const char *
checkBlob(X509 *x0, DataValue *blob, DataValue *partialDigest, uint64_t *savecid)
{
	int rv;
	X509 *x1, *x2;
	uint64_t thisecid;
	unsigned partial0;
	int len = blob->len;
	const unsigned char *ptr = blob->value;

	AppleImg3Header *cert = NULL;
	AppleImg3Header *ecid = NULL;
	AppleImg3Header *shsh = NULL;

	while (len > 0) {
		AppleImg3Header *hdr;
		if (len < sizeof(AppleImg3Header)) {
			return "truncated";
		}
		hdr = (AppleImg3Header *)ptr;
		flipAppleImg3Header(hdr); // XXX we need to flip ECID back before hashing
		switch (hdr->magic) {
			case IMG3_ECID_MAGIC:
				ecid = (AppleImg3Header *)ptr;
				break;
			case IMG3_SHSH_MAGIC:
				shsh = (AppleImg3Header *)ptr;
				break;
			case IMG3_CERT_MAGIC:
				cert = (AppleImg3Header *)ptr;
				break;
			default:
				return "unknown";
		}
		len -= hdr->size;
		ptr += hdr->size;
	}

	if (!ecid || !shsh || !cert) {
		return "incomplete";
	}
	partial0 = *(unsigned *)partialDigest->value;
	FLIPENDIANLE(partial0);
	if (partial0 != 0x40 || partial0 != ecid->size) {
		return "internal"; // XXX see doPartialSHA1()
	}

	thisecid = getECID(ecid + 1);
	if (*savecid == 0) {
		*savecid = thisecid;
	}
	if (*savecid != thisecid) {
		return "mismatch";
	}

	rv = extract2Certs((unsigned char *)(cert + 1), cert->dataSize, &x1, &x2);
	if (rv) {
		return "asn1";
	}

	rv = cryptoMagic(x0, x1, x2, (unsigned char *)ecid, ecid->size, (unsigned char *)(shsh + 1), shsh->dataSize, partialDigest);

	X509_free(x2);
	X509_free(x1);
	return rv ? "crypto" : NULL;
}