[USBSTOR][USBHUB]

- Append devobj number to device id
- Delete device objects
- Core-6598 

svn path=/trunk/; revision=57592
This commit is contained in:
Johannes Anderwald 2012-10-22 11:33:26 +00:00
parent b3643a80d5
commit 7983f1ff48
6 changed files with 87 additions and 19 deletions

View file

@ -819,6 +819,7 @@ CreateDeviceIds(
LPWSTR DeviceString; LPWSTR DeviceString;
WCHAR Buffer[200]; WCHAR Buffer[200];
PHUB_CHILDDEVICE_EXTENSION UsbChildExtension; PHUB_CHILDDEVICE_EXTENSION UsbChildExtension;
PHUB_DEVICE_EXTENSION HubDeviceExtension;
PUSB_DEVICE_DESCRIPTOR DeviceDescriptor; PUSB_DEVICE_DESCRIPTOR DeviceDescriptor;
PUSB_CONFIGURATION_DESCRIPTOR ConfigurationDescriptor; PUSB_CONFIGURATION_DESCRIPTOR ConfigurationDescriptor;
PUSB_INTERFACE_DESCRIPTOR InterfaceDescriptor; PUSB_INTERFACE_DESCRIPTOR InterfaceDescriptor;
@ -828,6 +829,9 @@ CreateDeviceIds(
// //
UsbChildExtension = (PHUB_CHILDDEVICE_EXTENSION)UsbChildDeviceObject->DeviceExtension; UsbChildExtension = (PHUB_CHILDDEVICE_EXTENSION)UsbChildDeviceObject->DeviceExtension;
// get hub device extension
HubDeviceExtension = (PHUB_DEVICE_EXTENSION) UsbChildExtension->ParentDeviceObject->DeviceExtension;
// //
// get device descriptor // get device descriptor
// //
@ -1011,10 +1015,12 @@ CreateDeviceIds(
// //
if (UsbChildExtension->DeviceDesc.iSerialNumber) if (UsbChildExtension->DeviceDesc.iSerialNumber)
{ {
LPWSTR SerialBuffer = NULL;
Status = GetUsbStringDescriptor(UsbChildDeviceObject, Status = GetUsbStringDescriptor(UsbChildDeviceObject,
UsbChildExtension->DeviceDesc.iSerialNumber, UsbChildExtension->DeviceDesc.iSerialNumber,
0, 0,
(PVOID*)&UsbChildExtension->usInstanceId.Buffer, (PVOID*)&SerialBuffer,
&UsbChildExtension->usInstanceId.Length); &UsbChildExtension->usInstanceId.Length);
if (!NT_SUCCESS(Status)) if (!NT_SUCCESS(Status))
{ {
@ -1022,15 +1028,31 @@ CreateDeviceIds(
return Status; return Status;
} }
UsbChildExtension->usInstanceId.MaximumLength = UsbChildExtension->usInstanceId.Length; // construct instance id buffer
DPRINT("Usb InstanceId %wZ\n", &UsbChildExtension->usInstanceId); Index = swprintf(Buffer, L"%04d&%s", HubDeviceExtension->InstanceCount, SerialBuffer) + 1;
UsbChildExtension->usInstanceId.Buffer = (LPWSTR)ExAllocatePool(NonPagedPool, Index * sizeof(WCHAR));
if (UsbChildExtension->usInstanceId.Buffer == NULL)
{
DPRINT1("Error: failed to allocate %lu bytes\n", Index * sizeof(WCHAR));
Status = STATUS_INSUFFICIENT_RESOURCES;
return Status;
}
//
// copy instance id
//
RtlCopyMemory(UsbChildExtension->usInstanceId.Buffer, Buffer, Index * sizeof(WCHAR));
UsbChildExtension->usInstanceId.Length = UsbChildExtension->usInstanceId.MaximumLength = Index * sizeof(WCHAR);
ExFreePool(SerialBuffer);
DPRINT("Usb InstanceId %wZ InstanceCount %x\n", &UsbChildExtension->usInstanceId, HubDeviceExtension->InstanceCount);
} }
else else
{ {
// //
// the device did not provide a serial number, lets create a pseudo instance id // the device did not provide a serial number, lets create a pseudo instance id
// //
Index = swprintf(Buffer, L"0&%04d", UsbChildExtension->PortNumber) + 1; Index = swprintf(Buffer, L"%04d&%04d", HubDeviceExtension->InstanceCount, UsbChildExtension->PortNumber) + 1;
UsbChildExtension->usInstanceId.Buffer = (LPWSTR)ExAllocatePool(NonPagedPool, Index * sizeof(WCHAR)); UsbChildExtension->usInstanceId.Buffer = (LPWSTR)ExAllocatePool(NonPagedPool, Index * sizeof(WCHAR));
if (UsbChildExtension->usInstanceId.Buffer == NULL) if (UsbChildExtension->usInstanceId.Buffer == NULL)
{ {
@ -1304,6 +1326,7 @@ CreateUsbChildDeviceObject(
} }
HubDeviceExtension->ChildDeviceObject[ChildDeviceCount] = NewChildDeviceObject; HubDeviceExtension->ChildDeviceObject[ChildDeviceCount] = NewChildDeviceObject;
HubDeviceExtension->InstanceCount++;
IoInvalidateDeviceRelations(RootHubDeviceObject, BusRelations); IoInvalidateDeviceRelations(RootHubDeviceObject, BusRelations);
return STATUS_SUCCESS; return STATUS_SUCCESS;

View file

@ -558,6 +558,7 @@ USBHUB_PdoHandlePnp(
ULONG Index; ULONG Index;
ULONG bFound; ULONG bFound;
PDEVICE_RELATIONS DeviceRelation; PDEVICE_RELATIONS DeviceRelation;
PDEVICE_OBJECT ParentDevice;
UsbChildExtension = (PHUB_CHILDDEVICE_EXTENSION)DeviceObject->DeviceExtension; UsbChildExtension = (PHUB_CHILDDEVICE_EXTENSION)DeviceObject->DeviceExtension;
Stack = IoGetCurrentIrpStackLocation(Irp); Stack = IoGetCurrentIrpStackLocation(Irp);
@ -645,6 +646,7 @@ USBHUB_PdoHandlePnp(
{ {
PHUB_DEVICE_EXTENSION HubDeviceExtension = (PHUB_DEVICE_EXTENSION)UsbChildExtension->ParentDeviceObject->DeviceExtension; PHUB_DEVICE_EXTENSION HubDeviceExtension = (PHUB_DEVICE_EXTENSION)UsbChildExtension->ParentDeviceObject->DeviceExtension;
PUSB_BUS_INTERFACE_HUB_V5 HubInterface = &HubDeviceExtension->HubInterface; PUSB_BUS_INTERFACE_HUB_V5 HubInterface = &HubDeviceExtension->HubInterface;
ParentDevice = UsbChildExtension->ParentDeviceObject;
DPRINT("IRP_MJ_PNP / IRP_MN_REMOVE_DEVICE\n"); DPRINT("IRP_MJ_PNP / IRP_MN_REMOVE_DEVICE\n");
@ -671,10 +673,13 @@ USBHUB_PdoHandlePnp(
Irp->IoStatus.Status = STATUS_SUCCESS; Irp->IoStatus.Status = STATUS_SUCCESS;
IoCompleteRequest(Irp, IO_NO_INCREMENT); IoCompleteRequest(Irp, IO_NO_INCREMENT);
/* delete device */
IoDeleteDevice(DeviceObject);
if (bFound) if (bFound)
{ {
/* Delete the device object */ /* invalidate device relations */
IoDeleteDevice(DeviceObject); IoInvalidateDeviceRelations(ParentDevice, BusRelations);
} }
return STATUS_SUCCESS; return STATUS_SUCCESS;
@ -731,6 +736,12 @@ USBHUB_PdoHandlePnp(
IoSkipCurrentIrpStackLocation(Irp); IoSkipCurrentIrpStackLocation(Irp);
return IoCallDriver(UsbChildExtension->ParentDeviceObject, Irp); return IoCallDriver(UsbChildExtension->ParentDeviceObject, Irp);
} }
case IRP_MN_SURPRISE_REMOVAL:
{
DPRINT("[USBHUB] HandlePnp IRP_MN_SURPRISE_REMOVAL\n");
Status = STATUS_SUCCESS;
break;
}
default: default:
{ {
DPRINT1("PDO IRP_MJ_PNP / unknown minor function 0x%lx\n", MinorFunction); DPRINT1("PDO IRP_MJ_PNP / unknown minor function 0x%lx\n", MinorFunction);

View file

@ -103,8 +103,9 @@ typedef struct _HUB_DEVICE_EXTENSION
PVOID RootHubHandle; PVOID RootHubHandle;
USB_BUS_INTERFACE_USBDI_V2 DeviceInterface; USB_BUS_INTERFACE_USBDI_V2 DeviceInterface;
UNICODE_STRING SymbolicLinkName; UNICODE_STRING SymbolicLinkName;
ULONG InstanceCount;
} HUB_DEVICE_EXTENSION, *PHUB_DEVICE_EXTENSION; } HUB_DEVICE_EXTENSION, *PHUB_DEVICE_EXTENSION;
// createclose.c // createclose.c

View file

@ -125,10 +125,19 @@ USBSTOR_FdoHandleRemoveDevice(
IN OUT PIRP Irp) IN OUT PIRP Irp)
{ {
NTSTATUS Status; NTSTATUS Status;
ULONG Index;
DPRINT("Handling FDO removal\n"); DPRINT("Handling FDO removal %p\n", DeviceObject);
/* We don't need to request removal of our children here */ /* FIXME: wait for devices finished processing */
for(Index = 0; Index < 16; Index++)
{
if (DeviceExtension->ChildPDO[Index] != NULL)
{
DPRINT("Deleting PDO %p RefCount %x AttachedDevice %p \n", DeviceExtension->ChildPDO[Index], DeviceExtension->ChildPDO[Index]->ReferenceCount, DeviceExtension->ChildPDO[Index]->AttachedDevice);
IoDeleteDevice(DeviceExtension->ChildPDO[Index]);
}
}
/* Send the IRP down the stack */ /* Send the IRP down the stack */
IoSkipCurrentIrpStackLocation(Irp); IoSkipCurrentIrpStackLocation(Irp);
@ -264,7 +273,7 @@ USBSTOR_FdoHandleStartDevice(
// //
// create pdo // create pdo
// //
Status = USBSTOR_CreatePDO(DeviceObject, Index, &DeviceExtension->ChildPDO[Index]); Status = USBSTOR_CreatePDO(DeviceObject, Index);
// //
// check for failure // check for failure
@ -282,6 +291,7 @@ USBSTOR_FdoHandleStartDevice(
// increment pdo index // increment pdo index
// //
Index++; Index++;
DeviceExtension->InstanceCount++;
}while(Index < DeviceExtension->MaxLUN); }while(Index < DeviceExtension->MaxLUN);
@ -340,8 +350,20 @@ USBSTOR_FdoHandlePnp(
switch(IoStack->MinorFunction) switch(IoStack->MinorFunction)
{ {
case IRP_MN_SURPRISE_REMOVAL:
{
DPRINT("IRP_MN_SURPRISE_REMOVAL %p\n", DeviceObject);
Irp->IoStatus.Status = STATUS_SUCCESS;
//
// forward irp to next device object
//
IoSkipCurrentIrpStackLocation(Irp);
return IoCallDriver(DeviceExtension->LowerDeviceObject, Irp);
}
case IRP_MN_QUERY_DEVICE_RELATIONS: case IRP_MN_QUERY_DEVICE_RELATIONS:
{ {
DPRINT("IRP_MN_QUERY_DEVICE_RELATIONS %p\n", DeviceObject);
Status = USBSTOR_FdoHandleDeviceRelations(DeviceExtension, Irp); Status = USBSTOR_FdoHandleDeviceRelations(DeviceExtension, Irp);
break; break;
} }

View file

@ -676,9 +676,9 @@ USBSTOR_PdoHandleQueryInstanceId(
else else
{ {
// //
// FIXME: should use some random value // use instance count and LUN
// //
swprintf(Buffer, L"%s&%d", L"00000000", PDODeviceExtension->LUN); swprintf(Buffer, L"%04d&%d", FDODeviceExtension->InstanceCount, PDODeviceExtension->LUN);
} }
// //
@ -897,7 +897,7 @@ USBSTOR_PdoHandlePnp(
// check if no unique id // check if no unique id
// //
Caps = (PDEVICE_CAPABILITIES)IoStack->Parameters.DeviceCapabilities.Capabilities; Caps = (PDEVICE_CAPABILITIES)IoStack->Parameters.DeviceCapabilities.Capabilities;
Caps->UniqueID = TRUE; //FIXME Caps->UniqueID = FALSE; // no unique id is supported
Caps->Removable = TRUE; //FIXME Caps->Removable = TRUE; //FIXME
} }
break; break;
@ -929,6 +929,11 @@ USBSTOR_PdoHandlePnp(
Status = STATUS_SUCCESS; Status = STATUS_SUCCESS;
break; break;
} }
case IRP_MN_SURPRISE_REMOVAL:
{
Status = STATUS_SUCCESS;
break;
}
default: default:
{ {
// //
@ -1256,13 +1261,19 @@ USBSTOR_SendFormatCapacityIrp(
NTSTATUS NTSTATUS
USBSTOR_CreatePDO( USBSTOR_CreatePDO(
IN PDEVICE_OBJECT DeviceObject, IN PDEVICE_OBJECT DeviceObject,
IN UCHAR LUN, IN UCHAR LUN)
OUT PDEVICE_OBJECT *ChildDeviceObject)
{ {
PDEVICE_OBJECT PDO; PDEVICE_OBJECT PDO;
NTSTATUS Status; NTSTATUS Status;
PPDO_DEVICE_EXTENSION PDODeviceExtension; PPDO_DEVICE_EXTENSION PDODeviceExtension;
PUFI_INQUIRY_RESPONSE Response; PUFI_INQUIRY_RESPONSE Response;
PFDO_DEVICE_EXTENSION FDODeviceExtension;
//
// get device extension
//
FDODeviceExtension = (PFDO_DEVICE_EXTENSION)DeviceObject->DeviceExtension;
// //
// create child device object // create child device object
@ -1292,7 +1303,7 @@ USBSTOR_CreatePDO(
RtlZeroMemory(PDODeviceExtension, sizeof(PDO_DEVICE_EXTENSION)); RtlZeroMemory(PDODeviceExtension, sizeof(PDO_DEVICE_EXTENSION));
PDODeviceExtension->Common.IsFDO = FALSE; PDODeviceExtension->Common.IsFDO = FALSE;
PDODeviceExtension->LowerDeviceObject = DeviceObject; PDODeviceExtension->LowerDeviceObject = DeviceObject;
PDODeviceExtension->PDODeviceObject = ChildDeviceObject; PDODeviceExtension->PDODeviceObject = &FDODeviceExtension->ChildPDO[LUN];
PDODeviceExtension->Self = PDO; PDODeviceExtension->Self = PDO;
PDODeviceExtension->LUN = LUN; PDODeviceExtension->LUN = LUN;
@ -1309,7 +1320,7 @@ USBSTOR_CreatePDO(
// //
// output device object // output device object
// //
*ChildDeviceObject = PDO; FDODeviceExtension->ChildPDO[LUN] = PDO;
// //
// send inquiry command by irp // send inquiry command by irp

View file

@ -71,6 +71,7 @@ typedef struct
PSCSI_REQUEST_BLOCK LastTimerActiveSrb; // last timer tick active srb PSCSI_REQUEST_BLOCK LastTimerActiveSrb; // last timer tick active srb
ULONG SrbErrorHandlingActive; // error handling of srb is activated ULONG SrbErrorHandlingActive; // error handling of srb is activated
ULONG TimerWorkQueueEnabled; // timer work queue enabled ULONG TimerWorkQueueEnabled; // timer work queue enabled
ULONG InstanceCount; // pdo instance count
}FDO_DEVICE_EXTENSION, *PFDO_DEVICE_EXTENSION; }FDO_DEVICE_EXTENSION, *PFDO_DEVICE_EXTENSION;
typedef struct typedef struct
@ -364,8 +365,7 @@ USBSTOR_PdoHandlePnp(
NTSTATUS NTSTATUS
USBSTOR_CreatePDO( USBSTOR_CreatePDO(
IN PDEVICE_OBJECT DeviceObject, IN PDEVICE_OBJECT DeviceObject,
IN UCHAR LUN, IN UCHAR LUN);
OUT PDEVICE_OBJECT *ChildDeviceObject);
//--------------------------------------------------------------------- //---------------------------------------------------------------------
// //