Used more specific exception classes to allow the TC to handle device failure errors better

This commit is contained in:
Nav
2021-08-15 01:47:48 +01:00
parent 89b5875132
commit 85fbf1ada4
16 changed files with 228 additions and 115 deletions

View File

@@ -1,11 +1,12 @@
#include "HidInterface.hpp"
#include <cstdint>
#include <string>
#include "HidInterface.hpp"
#include "hidapi.hpp"
#include "src/Logger/Logger.hpp"
#include "src/Exceptions/Exception.hpp"
#include "src/Exceptions/DeviceCommunicationFailure.hpp"
#include "src/TargetController/Exceptions/DeviceInitializationFailure.hpp"
#include "src/TargetController/Exceptions/DeviceCommunicationFailure.hpp"
using namespace Bloom::Usb;
using namespace Bloom::Exceptions;
@@ -22,7 +23,7 @@ std::string HidInterface::getDevicePathByInterfaceNumber(const std::uint16_t& in
}
if (hidDeviceInfoList == nullptr) {
throw Exception("Failed to match interface number with HID interface.");
throw DeviceInitializationFailure("Failed to match interface number with HID interface.");
}
auto path = std::string(hidDeviceInfoList->path);
@@ -32,7 +33,7 @@ std::string HidInterface::getDevicePathByInterfaceNumber(const std::uint16_t& in
void HidInterface::init() {
if (this->libUsbDevice == nullptr) {
throw Exception("Cannot initialise interface without libusb device pointer.");
throw DeviceInitializationFailure("Cannot initialise interface without libusb device pointer.");
}
hid_init();
@@ -42,11 +43,13 @@ void HidInterface::init() {
Logger::debug("HID device path: " + hidInterfacePath);
if ((hidDevice = hid_open_path(hidInterfacePath.c_str())) == nullptr) {
throw Exception("Failed to open HID device via hidapi.");
throw DeviceInitializationFailure("Failed to open HID device via hidapi.");
}
if (hidDevice->input_ep_max_packet_size < 1) {
throw Exception("Invalid max packet size for USB endpoint, on interface " + std::to_string(this->getNumber()));
throw DeviceInitializationFailure(
"Invalid max packet size for USB endpoint, on interface " + std::to_string(this->getNumber())
);
}
this->setHidDevice(hidDevice);
@@ -87,7 +90,9 @@ std::size_t HidInterface::read(unsigned char* buffer, std::size_t maxLength, uns
void HidInterface::write(std::vector<unsigned char> buffer) {
if (buffer.size() > this->getInputReportSize()) {
throw Exception("Cannot send data via HID interface - data exceeds maximum packet size.");
throw DeviceCommunicationFailure(
"Cannot send data via HID interface - data exceeds maximum packet size."
);
} else if (buffer.size() < this->getInputReportSize()) {
/*

View File

@@ -1,20 +1,22 @@
#include "Interface.hpp"
#include <libusb-1.0/libusb.h>
#include <chrono>
#include "Interface.hpp"
#include "src/Exceptions/Exception.hpp"
#include "src/TargetController/Exceptions/DeviceFailure.hpp"
#include "src/TargetController/Exceptions/DeviceCommunicationFailure.hpp"
#include "src/TargetController/Exceptions/DeviceInitializationFailure.hpp"
using namespace Bloom::Usb;
using namespace Bloom::Exceptions;
void Interface::init() {
if (this->libUsbDevice == nullptr) {
throw Exception("Cannot initialise interface without libusb device pointer.");
throw DeviceInitializationFailure("Cannot initialise interface without libusb device pointer.");
}
if (this->libUsbDeviceHandle == nullptr) {
throw Exception("Cannot initialise interface without libusb device handle.");
throw DeviceInitializationFailure("Cannot initialise interface without libusb device handle.");
}
this->initialised = true;
@@ -34,7 +36,9 @@ void Interface::claim() {
this->detachKernelDriver();
if (libusb_claim_interface(this->libUsbDeviceHandle, interfaceNumber) != 0) {
throw Exception("Failed to claim interface {" + std::to_string(interfaceNumber) + "} on USB device\n");
throw DeviceInitializationFailure(
"Failed to claim interface {" + std::to_string(interfaceNumber) + "} on USB device\n"
);
}
this->claimed = true;
@@ -48,11 +52,11 @@ void Interface::detachKernelDriver() {
if (libUsbStatusCode == 1) {
// A kernel driver is active on this interface. Attempt to detach it
if (libusb_detach_kernel_driver(this->libUsbDeviceHandle, interfaceNumber) != 0) {
throw Exception("Failed to detach kernel driver from interface " +
throw DeviceInitializationFailure("Failed to detach kernel driver from interface " +
std::to_string(interfaceNumber) + "\n");
}
} else {
throw Exception("Failed to check for active kernel driver on USB interface.");
throw DeviceInitializationFailure("Failed to check for active kernel driver on USB interface.");
}
}
}
@@ -60,7 +64,9 @@ void Interface::detachKernelDriver() {
void Interface::release() {
if (this->isClaimed()) {
if (libusb_release_interface(this->libUsbDeviceHandle, this->getNumber()) != 0) {
throw Exception("Failed to release interface {" + std::to_string(this->getNumber()) + "} on USB device\n");
throw DeviceFailure(
"Failed to release interface {" + std::to_string(this->getNumber()) + "} on USB device\n"
);
}
this->claimed = false;
@@ -83,7 +89,9 @@ int Interface::read(unsigned char* buffer, unsigned char endPoint, size_t length
);
if (libUsbStatusCode != 0 && libUsbStatusCode != -7) {
throw Exception("Failed to read from USB device. Error code returned: " + std::to_string(libUsbStatusCode));
throw DeviceCommunicationFailure(
"Failed to read from USB device. Error code returned: " + std::to_string(libUsbStatusCode)
);
}
totalTransferred += transferred;
@@ -106,6 +114,8 @@ void Interface::write(unsigned char* buffer, unsigned char endPoint, int length)
);
if (libUsbStatusCode != 0) {
throw Exception("Failed to read from USB device. Error code returned: " + std::to_string(libUsbStatusCode));
throw DeviceCommunicationFailure(
"Failed to read from USB device. Error code returned: " + std::to_string(libUsbStatusCode)
);
}
}

View File

@@ -1,9 +1,10 @@
#include "UsbDevice.hpp"
#include <cstdint>
#include <libusb-1.0/libusb.h>
#include "UsbDevice.hpp"
#include "src/Logger/Logger.hpp"
#include "src/Exceptions/Exception.hpp"
#include "src/TargetController/Exceptions/DeviceInitializationFailure.hpp"
using Bloom::Usb::UsbDevice;
using namespace Bloom::Exceptions;
@@ -21,8 +22,9 @@ std::vector<libusb_device*> UsbDevice::findMatchingDevices(
auto productIdToMatch = productId.value_or(this->productId);
if ((libUsbStatusCode = libusb_get_device_list(libUsbContext, &devices)) < 0) {
throw Exception("Failed to retrieve USB devices - return code: '" + std::to_string(libUsbStatusCode)
+ "'");
throw DeviceInitializationFailure(
"Failed to retrieve USB devices - return code: '" + std::to_string(libUsbStatusCode) + "'"
);
}
while ((device = devices[i++]) != nullptr) {
@@ -30,7 +32,7 @@ std::vector<libusb_device*> UsbDevice::findMatchingDevices(
if ((libUsbStatusCode = libusb_get_device_descriptor(device, &desc)) < 0) {
Logger::warning("Failed to retrieve USB device descriptor - return code: '"
+ std::to_string(libUsbStatusCode) + "'");
+ std::to_string(libUsbStatusCode) + "'");
continue;
}
@@ -49,14 +51,14 @@ void UsbDevice::init() {
auto devices = this->findMatchingDevices();
if (devices.empty()) {
throw Exception("Failed to find USB device with matching vendor & product ID.");
throw DeviceInitializationFailure("Failed to find USB device with matching vendor & product ID.");
} else if (devices.size() > 1) {
// TODO: implement support for multiple devices (maybe via serial number?)
throw Exception("Multiple devices of matching vendor & product ID found.\n"
"Yes, as a program I really am too stupid to figure out what to do "
"here, so I'm just going to quit.\n Please ensure that only one debug tool "
"is connected and then try again.");
throw DeviceInitializationFailure(
"Numerous devices of matching vendor & product ID found.\n"
"Please ensure that only one debug tool is connected and then try again."
);
}
// For now, just use the first device found.
@@ -67,8 +69,9 @@ void UsbDevice::init() {
// Obtain a device handle from libusb
if ((libUsbStatusCode = libusb_open(libUsbDevice, &this->libUsbDeviceHandle)) < 0) {
throw Exception("Failed to open USB device - error code " + std::to_string(libUsbStatusCode)
+ " returned.");
throw DeviceInitializationFailure(
"Failed to open USB device - error code " + std::to_string(libUsbStatusCode) + " returned."
);
}
}
@@ -88,13 +91,16 @@ void UsbDevice::setConfiguration(int configIndex) {
int libUsbStatusCode;
if ((libUsbStatusCode = libusb_get_config_descriptor(this->libUsbDevice, 0, &configDescriptor))) {
throw Exception("Failed to obtain USB configuration descriptor - error code "
+ std::to_string(libUsbStatusCode) + " returned.");
throw DeviceInitializationFailure(
"Failed to obtain USB configuration descriptor - error code " + std::to_string(libUsbStatusCode)
+ " returned."
);
}
if ((libUsbStatusCode = libusb_set_configuration(this->libUsbDeviceHandle, configDescriptor->bConfigurationValue))) {
throw Exception("Failed to set USB configuration - error code "
+ std::to_string(libUsbStatusCode) + " returned.");
throw DeviceInitializationFailure(
"Failed to set USB configuration - error code " + std::to_string(libUsbStatusCode) + " returned."
);
}
libusb_free_config_descriptor(configDescriptor);