Working arduino control requests, still kind of clunky
This commit is contained in:
@@ -8,7 +8,7 @@ add_executable(checkm8_remote main.c src/usb_helpers.c src/exploit.c src/payload
|
||||
add_custom_command(TARGET checkm8_remote POST_BUILD
|
||||
COMMAND ln
|
||||
ARGS -s -f -n
|
||||
${PROJECT_SOURCE_DIR}/checkm8_payloads/bin
|
||||
${CMAKE_SOURCE_DIR}/checkm8_payloads/bin
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/bin/payloads)
|
||||
|
||||
target_link_libraries(checkm8_remote checkm8_libusb pthread udev)
|
||||
@@ -40,55 +40,55 @@ 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;
|
||||
// }
|
||||
//
|
||||
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);
|
||||
//
|
||||
@@ -97,7 +97,7 @@ int main()
|
||||
// printf("Failed to execute AES\n");
|
||||
// return -1;
|
||||
// }
|
||||
//
|
||||
// free_dev_cmd_resp(resp);
|
||||
// free_device(dev);
|
||||
|
||||
free_dev_cmd_resp(resp);
|
||||
free_device(dev);
|
||||
}
|
||||
|
||||
@@ -29,7 +29,7 @@ int dfu_send_data(struct pwned_device *dev, unsigned char *data, long data_len)
|
||||
if(ret > 0) checkm8_debug_indent("\ttransferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\trequest failed with error code %i (%s)\n", ret, libusb_error_name(ret));
|
||||
checkm8_debug_indent("\trequest failed with error code %i\n", ret);
|
||||
return CHECKM8_FAIL_XFER;
|
||||
}
|
||||
index += amount;
|
||||
@@ -67,7 +67,7 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
if(ret >= 0) checkm8_debug_indent("\ttransferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\trequest failed with error code %i (%s)\n", ret, libusb_error_name(ret));
|
||||
checkm8_debug_indent("\trequest failed with error code %i\n", ret);
|
||||
cmd_resp->ret = ret;
|
||||
return cmd_resp;
|
||||
}
|
||||
@@ -76,7 +76,7 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
if(ret >= 0) checkm8_debug_indent("\ttransferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\trequest failed with error code %i (%s)\n", ret, libusb_error_name(ret));
|
||||
checkm8_debug_indent("\trequest failed with error code %i\n", ret);
|
||||
cmd_resp->ret = ret;
|
||||
return cmd_resp;
|
||||
}
|
||||
@@ -85,7 +85,7 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
if(ret >= 0) checkm8_debug_indent("\ttransferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\trequest failed with error code %i (%s)\n", ret, libusb_error_name(ret));
|
||||
checkm8_debug_indent("\trequest failed with error code %i\n", ret);
|
||||
cmd_resp->ret = ret;
|
||||
return cmd_resp;
|
||||
}
|
||||
@@ -106,7 +106,7 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
if(ret >= 0) checkm8_debug_indent("\tfinal request transferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\tfinal request failed with error code %i (%s)\n", ret, libusb_error_name(ret));
|
||||
checkm8_debug_indent("\tfinal request failed with error code %i\n", ret);
|
||||
cmd_resp->ret = ret;
|
||||
return cmd_resp;
|
||||
}
|
||||
@@ -120,7 +120,7 @@ struct dev_cmd_resp *command(struct pwned_device *dev,
|
||||
if(ret >= 0) checkm8_debug_indent("\tfinal request transferred %i bytes\n", ret);
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\tfinal request failed with error code %i (%s)\n", ret, libusb_error_name(ret));
|
||||
checkm8_debug_indent("\tfinal request failed with error code %i\n", ret);
|
||||
cmd_resp->ret = ret;
|
||||
return cmd_resp;
|
||||
}
|
||||
|
||||
@@ -43,6 +43,7 @@ struct payload *get_payload(PAYLOAD_T p)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
checkm8_debug_indent("get_payload(p = %i) -> %s\n", p, path);
|
||||
res = malloc(sizeof(struct payload));
|
||||
if(res == NULL) return NULL;
|
||||
|
||||
@@ -131,12 +132,16 @@ int *dev_unlink_payload(struct pwned_device *dev, struct payload *pl)
|
||||
int install_payload(struct pwned_device *dev, PAYLOAD_T p, LOCATION_T loc)
|
||||
{
|
||||
checkm8_debug_indent("install_payload(dev = %p, p = %i, loc = %i)\n", dev, p, loc);
|
||||
int i, ret;
|
||||
int ret;
|
||||
struct dev_cmd_resp *resp = NULL;
|
||||
struct payload *pl = get_payload(p);
|
||||
long long addr = get_address(dev, loc);
|
||||
|
||||
if(pl == NULL || addr == -1) return CHECKM8_FAIL_INVARGS;
|
||||
if(pl == NULL || addr == -1)
|
||||
{
|
||||
checkm8_debug_indent("\tinvalid args (either payload or address)\n");
|
||||
return CHECKM8_FAIL_INVARGS;
|
||||
}
|
||||
|
||||
ret = open_device_session(dev);
|
||||
if(IS_CHECKM8_FAIL(ret)) return ret;
|
||||
@@ -161,6 +166,7 @@ int install_payload(struct pwned_device *dev, PAYLOAD_T p, LOCATION_T loc)
|
||||
int uninstall_payload(struct pwned_device *dev, PAYLOAD_T p)
|
||||
{
|
||||
//TODO: free memory in memory allocator
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
|
||||
struct dev_cmd_resp *execute_payload(struct pwned_device *dev, PAYLOAD_T p, int nargs, ...)
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
#include "usb_helpers.h"
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#ifdef WITH_ARDUINO
|
||||
|
||||
#include <termio.h>
|
||||
@@ -12,6 +10,7 @@
|
||||
#else
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include "libusbi.h"
|
||||
|
||||
#endif
|
||||
@@ -401,7 +400,8 @@ int no_error_ctrl_transfer(struct pwned_device *dev,
|
||||
}
|
||||
}
|
||||
|
||||
ret = libusb_control_transfer(dev->bundle->handle, bmRequestType, bRequest, wValue, wIndex, data, data_len, timeout);
|
||||
ret = libusb_control_transfer(dev->bundle->handle, bmRequestType, bRequest, wValue, wIndex, data, data_len,
|
||||
timeout);
|
||||
checkm8_debug_indent("\tgot error %s but ignoring\n", libusb_error_name(ret));
|
||||
return CHECKM8_SUCCESS;
|
||||
#endif
|
||||
@@ -434,7 +434,6 @@ int no_error_ctrl_transfer_data(struct pwned_device *dev,
|
||||
if(buf == PROT_ACK)
|
||||
{
|
||||
checkm8_debug_indent("\treceived argument ack\n");
|
||||
|
||||
while(index < data_len)
|
||||
{
|
||||
if(data_len - index > ARD_BUF_SIZE) amount = ARD_BUF_SIZE;
|
||||
@@ -442,19 +441,18 @@ int no_error_ctrl_transfer_data(struct pwned_device *dev,
|
||||
|
||||
checkm8_debug_indent("\twriting data chunk of size %i\n", amount);
|
||||
write(dev->ard_fd, &data[index], amount);
|
||||
do
|
||||
|
||||
while(read(dev->ard_fd, &buf, 1) == 0);
|
||||
if(buf == PROT_ACK)
|
||||
{
|
||||
if(buf == PROT_FAIL_USB)
|
||||
{
|
||||
while(read(dev->ard_fd, &buf, 1) == 0);
|
||||
checkm8_debug_indent("\treceived error %X but ignoring\n", buf);
|
||||
}
|
||||
|
||||
while(read(dev->ard_fd, &buf, 1) == 0);
|
||||
} while(buf != PROT_ACK);
|
||||
|
||||
checkm8_debug_indent("\treceived data ack\n");
|
||||
index += amount;
|
||||
checkm8_debug_indent("\treceived data ack\n");
|
||||
index += amount;
|
||||
}
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\treceived unexpected response %x\n", buf);
|
||||
return CHECKM8_FAIL_PROT;
|
||||
}
|
||||
}
|
||||
|
||||
while(read(dev->ard_fd, &buf, 1) == 0);
|
||||
@@ -463,6 +461,11 @@ int no_error_ctrl_transfer_data(struct pwned_device *dev,
|
||||
checkm8_debug_indent("\tsuccess\n");
|
||||
return CHECKM8_SUCCESS;
|
||||
}
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\tunexpected response %x\n", buf);
|
||||
return CHECKM8_FAIL_PROT;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -481,10 +484,11 @@ int ctrl_transfer(struct pwned_device *dev,
|
||||
unsigned int timeout)
|
||||
{
|
||||
checkm8_debug_indent(
|
||||
"ctrl_transfer(dev = %p, bmRequestType = %i, bRequest = %i, wValue = %i, wIndex = %i, data = %p, data_len = %i, timeout = %i)\n",
|
||||
"ctrl_transfer(dev = %p, bmRequestType = %X, bRequest = %X, wValue = %i, wIndex = %i, data = %p, data_len = %i, timeout = %i)\n",
|
||||
dev, bmRequestType, bRequest, wValue, wIndex, data, data_len, timeout);
|
||||
|
||||
#ifdef WITH_ARDUINO
|
||||
int amount, index;
|
||||
char buf;
|
||||
struct usb_xfer_args args;
|
||||
args.bmRequestType = bmRequestType;
|
||||
@@ -496,32 +500,63 @@ int ctrl_transfer(struct pwned_device *dev,
|
||||
checkm8_debug_indent("\tsending data to arduino\n");
|
||||
write(dev->ard_fd, &PROT_CTRL_XFER, 1);
|
||||
write(dev->ard_fd, &args, sizeof(struct usb_xfer_args));
|
||||
write(dev->ard_fd, data, data_len);
|
||||
|
||||
while(read(dev->ard_fd, &buf, 1) == 0);
|
||||
if(buf == PROT_ACK)
|
||||
{
|
||||
checkm8_debug_indent("\treceived ack\n");
|
||||
checkm8_debug_indent("\treceived argument ack\n");
|
||||
if(bmRequestType & 0x80)
|
||||
{
|
||||
amount = 0;
|
||||
while(amount < data_len)
|
||||
{
|
||||
// get the size of this chunk
|
||||
while(read(dev->ard_fd, &buf, 1) == 0);
|
||||
checkm8_debug_indent("\treceiving data chunk of size %i\n", buf);
|
||||
|
||||
while(read(dev->ard_fd, &buf, 1) == 0);
|
||||
if(buf == PROT_FAIL_TOOBIG)
|
||||
{
|
||||
checkm8_debug_indent("\tdata packet is too big\n");
|
||||
return CHECKM8_FAIL_INVARGS;
|
||||
}
|
||||
else if(buf == PROT_FAIL_USB)
|
||||
{
|
||||
while(read(dev->ard_fd, &buf, 1) == 0);
|
||||
checkm8_debug_indent("\tUSB failed with error %x\n", buf);
|
||||
}
|
||||
else if(buf == PROT_SUCCESS)
|
||||
{
|
||||
checkm8_debug_indent("\tsuccess\n");
|
||||
return CHECKM8_SUCCESS;
|
||||
index = 0;
|
||||
while(index < buf)
|
||||
{
|
||||
index += read(dev->ard_fd, &data[amount + index], buf - index);
|
||||
}
|
||||
|
||||
amount += buf;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\tunexpected response %X\n", buf);
|
||||
index = 0;
|
||||
while(index < data_len)
|
||||
{
|
||||
if(data_len - index > ARD_BUF_SIZE) amount = ARD_BUF_SIZE;
|
||||
else amount = data_len - index;
|
||||
|
||||
checkm8_debug_indent("\twriting data chunk of size %i\n", amount);
|
||||
write(dev->ard_fd, &data[index], amount);
|
||||
|
||||
while(read(dev->ard_fd, &buf, 1) == 0);
|
||||
if(buf == PROT_ACK)
|
||||
{
|
||||
checkm8_debug_indent("\treceived data ack\n");
|
||||
index += amount;
|
||||
}
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\treceived unexpected response %x\n", buf);
|
||||
return CHECKM8_FAIL_PROT;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
while(read(dev->ard_fd, &buf, 1) == 0);
|
||||
if(buf == PROT_SUCCESS)
|
||||
{
|
||||
checkm8_debug_indent("\tsuccess\n");
|
||||
return data_len;
|
||||
}
|
||||
else
|
||||
{
|
||||
checkm8_debug_indent("\tunexpected response %x\n", buf);
|
||||
return CHECKM8_FAIL_PROT;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user