* Clear the configurations list so it can safely be handled in case the device
fails to init completely. * Fix wrong usage of realloc and check the allocations. * Check a few more allocations, should be all now. * Fix a small memory leaks in error case. * Do a few more checks when unconfiguring and deleting a device so an incompletely initilized device is deleted correctly and does not crash or leak. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@25654 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -73,6 +73,8 @@ Device::Device(Object *parent, int8 hubPort, usb_device_descriptor &desc,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
memset(fConfigurations, 0, fDeviceDescriptor.num_configurations
|
||||||
|
* sizeof(usb_configuration_info));
|
||||||
for (int32 i = 0; i < fDeviceDescriptor.num_configurations; i++) {
|
for (int32 i = 0; i < fDeviceDescriptor.num_configurations; i++) {
|
||||||
usb_configuration_descriptor configDescriptor;
|
usb_configuration_descriptor configDescriptor;
|
||||||
status = GetDescriptor(USB_DESCRIPTOR_CONFIGURATION, i, 0,
|
status = GetDescriptor(USB_DESCRIPTOR_CONFIGURATION, i, 0,
|
||||||
@@ -96,12 +98,20 @@ Device::Device(Object *parent, int8 hubPort, usb_device_descriptor &desc,
|
|||||||
TRACE(("\tmax_power:...........%d\n", configDescriptor.max_power));
|
TRACE(("\tmax_power:...........%d\n", configDescriptor.max_power));
|
||||||
|
|
||||||
uint8 *configData = (uint8 *)malloc(configDescriptor.total_length);
|
uint8 *configData = (uint8 *)malloc(configDescriptor.total_length);
|
||||||
|
if (configData == NULL) {
|
||||||
|
TRACE_ERROR(("USB Device %d: out of memory when reading config\n",
|
||||||
|
fDeviceAddress));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
status = GetDescriptor(USB_DESCRIPTOR_CONFIGURATION, i, 0,
|
status = GetDescriptor(USB_DESCRIPTOR_CONFIGURATION, i, 0,
|
||||||
(void *)configData, configDescriptor.total_length, &actualLength);
|
(void *)configData, configDescriptor.total_length, &actualLength);
|
||||||
|
|
||||||
if (status < B_OK || actualLength != configDescriptor.total_length) {
|
if (status < B_OK || actualLength != configDescriptor.total_length) {
|
||||||
TRACE_ERROR(("USB Device %d: error fetching full configuration"
|
TRACE_ERROR(("USB Device %d: error fetching full configuration"
|
||||||
" descriptor %ld\n", fDeviceAddress, i));
|
" descriptor %ld got %lu expected %u\n", fDeviceAddress, i,
|
||||||
|
actualLength, configDescriptor.total_length));
|
||||||
|
free(configData);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -111,6 +121,12 @@ Device::Device(Object *parent, int8 hubPort, usb_device_descriptor &desc,
|
|||||||
fConfigurations[i].interface_count = configuration->number_interfaces;
|
fConfigurations[i].interface_count = configuration->number_interfaces;
|
||||||
fConfigurations[i].interface = (usb_interface_list *)malloc(
|
fConfigurations[i].interface = (usb_interface_list *)malloc(
|
||||||
configuration->number_interfaces * sizeof(usb_interface_list));
|
configuration->number_interfaces * sizeof(usb_interface_list));
|
||||||
|
if (fConfigurations[i].interface == NULL) {
|
||||||
|
TRACE_ERROR(("USB Device %d: out of memory when creating interfaces\n",
|
||||||
|
fDeviceAddress));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
memset(fConfigurations[i].interface, 0,
|
memset(fConfigurations[i].interface, 0,
|
||||||
configuration->number_interfaces * sizeof(usb_interface_list));
|
configuration->number_interfaces * sizeof(usb_interface_list));
|
||||||
|
|
||||||
@@ -137,9 +153,17 @@ Device::Device(Object *parent, int8 hubPort, usb_device_descriptor &desc,
|
|||||||
|
|
||||||
/* Allocate this alternate */
|
/* Allocate this alternate */
|
||||||
interfaceList->alt_count++;
|
interfaceList->alt_count++;
|
||||||
interfaceList->alt = (usb_interface_info *)realloc(
|
usb_interface_info *newAlternates
|
||||||
interfaceList->alt, interfaceList->alt_count
|
= (usb_interface_info *)realloc(interfaceList->alt,
|
||||||
* sizeof(usb_interface_info));
|
interfaceList->alt_count * sizeof(usb_interface_info));
|
||||||
|
if (newAlternates == NULL) {
|
||||||
|
TRACE_ERROR(("USB Device %d: out of memory allocating"
|
||||||
|
" alternate interface\n", fDeviceAddress));
|
||||||
|
interfaceList->alt_count--;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
interfaceList->alt = newAlternates;
|
||||||
|
|
||||||
/* Set active interface always to the first one */
|
/* Set active interface always to the first one */
|
||||||
interfaceList->active = interfaceList->alt;
|
interfaceList->active = interfaceList->alt;
|
||||||
@@ -155,8 +179,13 @@ Device::Device(Object *parent, int8 hubPort, usb_device_descriptor &desc,
|
|||||||
|
|
||||||
Interface *interface = new(std::nothrow) Interface(this,
|
Interface *interface = new(std::nothrow) Interface(this,
|
||||||
interfaceDescriptor->interface_number);
|
interfaceDescriptor->interface_number);
|
||||||
interfaceInfo->handle = interface->USBID();
|
if (interface == NULL) {
|
||||||
|
TRACE_ERROR(("USB Device %d: failed to allocate"
|
||||||
|
" interface object\n", fDeviceAddress));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
interfaceInfo->handle = interface->USBID();
|
||||||
currentInterface = interfaceInfo;
|
currentInterface = interfaceInfo;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -177,10 +206,19 @@ Device::Device(Object *parent, int8 hubPort, usb_device_descriptor &desc,
|
|||||||
|
|
||||||
/* allocate this endpoint */
|
/* allocate this endpoint */
|
||||||
currentInterface->endpoint_count++;
|
currentInterface->endpoint_count++;
|
||||||
currentInterface->endpoint = (usb_endpoint_info *)realloc(
|
usb_endpoint_info *newEndpoints
|
||||||
|
= (usb_endpoint_info *)realloc(
|
||||||
currentInterface->endpoint,
|
currentInterface->endpoint,
|
||||||
currentInterface->endpoint_count
|
currentInterface->endpoint_count
|
||||||
* sizeof(usb_endpoint_info));
|
* sizeof(usb_endpoint_info));
|
||||||
|
if (newEndpoints == NULL) {
|
||||||
|
TRACE_ERROR(("USB Device %d: out of memory allocating"
|
||||||
|
" new endpoint\n", fDeviceAddress));
|
||||||
|
currentInterface->endpoint_count--;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
currentInterface->endpoint = newEndpoints;
|
||||||
|
|
||||||
/* setup this endpoint */
|
/* setup this endpoint */
|
||||||
usb_endpoint_info *endpointInfo =
|
usb_endpoint_info *endpointInfo =
|
||||||
@@ -202,10 +240,18 @@ Device::Device(Object *parent, int8 hubPort, usb_device_descriptor &desc,
|
|||||||
|
|
||||||
/* allocate this descriptor */
|
/* allocate this descriptor */
|
||||||
currentInterface->generic_count++;
|
currentInterface->generic_count++;
|
||||||
currentInterface->generic = (usb_descriptor **)realloc(
|
usb_descriptor **newGenerics = (usb_descriptor **)realloc(
|
||||||
currentInterface->generic,
|
currentInterface->generic,
|
||||||
currentInterface->generic_count
|
currentInterface->generic_count
|
||||||
* sizeof(usb_descriptor *));
|
* sizeof(usb_descriptor *));
|
||||||
|
if (newGenerics == NULL) {
|
||||||
|
TRACE_ERROR(("USB Device %d: out of memory allocating"
|
||||||
|
" generic descriptor\n", fDeviceAddress));
|
||||||
|
currentInterface->generic_count--;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
currentInterface->generic = newGenerics;
|
||||||
|
|
||||||
/* add this descriptor */
|
/* add this descriptor */
|
||||||
currentInterface->generic[currentInterface->generic_count - 1] =
|
currentInterface->generic[currentInterface->generic_count - 1] =
|
||||||
@@ -239,8 +285,18 @@ Device::~Device()
|
|||||||
// Free all allocated resources
|
// Free all allocated resources
|
||||||
for (int32 i = 0; i < fDeviceDescriptor.num_configurations; i++) {
|
for (int32 i = 0; i < fDeviceDescriptor.num_configurations; i++) {
|
||||||
usb_configuration_info *configuration = &fConfigurations[i];
|
usb_configuration_info *configuration = &fConfigurations[i];
|
||||||
|
if (configuration == NULL)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
free(configuration->descr);
|
||||||
|
if (configuration->interface == NULL)
|
||||||
|
continue;
|
||||||
|
|
||||||
for (size_t j = 0; j < configuration->interface_count; j++) {
|
for (size_t j = 0; j < configuration->interface_count; j++) {
|
||||||
usb_interface_list *interfaceList = &configuration->interface[j];
|
usb_interface_list *interfaceList = &configuration->interface[j];
|
||||||
|
if (interfaceList->alt == NULL)
|
||||||
|
continue;
|
||||||
|
|
||||||
for (size_t k = 0; k < interfaceList->alt_count; k++) {
|
for (size_t k = 0; k < interfaceList->alt_count; k++) {
|
||||||
usb_interface_info *interface = &interfaceList->alt[k];
|
usb_interface_info *interface = &interfaceList->alt[k];
|
||||||
delete (Interface *)GetStack()->GetObject(interface->handle);
|
delete (Interface *)GetStack()->GetObject(interface->handle);
|
||||||
@@ -252,7 +308,6 @@ Device::~Device()
|
|||||||
}
|
}
|
||||||
|
|
||||||
free(configuration->interface);
|
free(configuration->interface);
|
||||||
free(configuration->descr);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
free(fConfigurations);
|
free(fConfigurations);
|
||||||
@@ -463,11 +518,17 @@ Device::Unconfigure(bool atDeviceLevel)
|
|||||||
void
|
void
|
||||||
Device::ClearEndpoints(int32 interfaceIndex)
|
Device::ClearEndpoints(int32 interfaceIndex)
|
||||||
{
|
{
|
||||||
|
if (fCurrentConfiguration == NULL || fCurrentConfiguration->interface == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
for (size_t j = 0; j < fCurrentConfiguration->interface_count; j++) {
|
for (size_t j = 0; j < fCurrentConfiguration->interface_count; j++) {
|
||||||
if (interfaceIndex >= 0 && j != (size_t)interfaceIndex)
|
if (interfaceIndex >= 0 && j != (size_t)interfaceIndex)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
usb_interface_info *interfaceInfo = fCurrentConfiguration->interface[j].active;
|
usb_interface_info *interfaceInfo = fCurrentConfiguration->interface[j].active;
|
||||||
|
if (interfaceInfo == NULL || interfaceInfo->endpoint == NULL)
|
||||||
|
continue;
|
||||||
|
|
||||||
for (size_t i = 0; i < interfaceInfo->endpoint_count; i++) {
|
for (size_t i = 0; i < interfaceInfo->endpoint_count; i++) {
|
||||||
usb_endpoint_info *endpoint = &interfaceInfo->endpoint[i];
|
usb_endpoint_info *endpoint = &interfaceInfo->endpoint[i];
|
||||||
delete (Pipe *)GetStack()->GetObject(endpoint->handle);
|
delete (Pipe *)GetStack()->GetObject(endpoint->handle);
|
||||||
|
|||||||
Reference in New Issue
Block a user