Author: fireball
Date: Sat Jul 7 13:56:55 2007
New Revision: 27446
URL:
http://svn.reactos.org/svn/reactos?rev=27446&view=rev
Log:
- Separate common buffer allocation routine from ScsiPortGetUncachedExtension() into
SpiAllocateCommonBuffer(), along with a code reformat.
- Use this function in ScsiPortInitialize() and in ScsiPortGetUncachedExtension().
Modified:
trunk/reactos/drivers/storage/scsiport/scsiport.c
Modified: trunk/reactos/drivers/storage/scsiport/scsiport.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/storage/scsiport/s…
==============================================================================
--- trunk/reactos/drivers/storage/scsiport/scsiport.c (original)
+++ trunk/reactos/drivers/storage/scsiport/scsiport.c Sat Jul 7 13:56:55 2007
@@ -204,6 +204,10 @@
SpiHandleAttachRelease(PSCSI_PORT_DEVICE_EXTENSION DeviceExtension,
PIRP Irp);
+static NTSTATUS
+SpiAllocateCommonBuffer(PSCSI_PORT_DEVICE_EXTENSION DeviceExtension, ULONG
NonCachedSize);
+
+
/* FUNCTIONS *****************************************************************/
@@ -599,70 +603,178 @@
IN PPORT_CONFIGURATION_INFORMATION ConfigInfo,
IN ULONG NumberOfBytes)
{
- PSCSI_PORT_DEVICE_EXTENSION DeviceExtension;
- DEVICE_DESCRIPTION DeviceDescription;
-
- DPRINT("ScsiPortGetUncachedExtension(%p %p %lu)\n",
- HwDeviceExtension, ConfigInfo, NumberOfBytes);
-
- DeviceExtension = CONTAINING_RECORD(HwDeviceExtension,
- SCSI_PORT_DEVICE_EXTENSION,
- MiniPortDeviceExtension);
-
- /* Check for allocated common DMA buffer */
- if (DeviceExtension->VirtualAddress != NULL)
- {
- DPRINT1("The HBA has already got a common DMA buffer!\n");
- return NULL;
- }
-
- /* Check for DMA adapter object */
- if (DeviceExtension->AdapterObject == NULL)
- {
- /* Initialize DMA adapter description */
- RtlZeroMemory(&DeviceDescription,
- sizeof(DEVICE_DESCRIPTION));
- DeviceDescription.Version = DEVICE_DESCRIPTION_VERSION;
- DeviceDescription.Master = ConfigInfo->Master;
- DeviceDescription.ScatterGather = ConfigInfo->ScatterGather;
- DeviceDescription.DemandMode = ConfigInfo->DemandMode;
- DeviceDescription.Dma32BitAddresses = ConfigInfo->Dma32BitAddresses;
- DeviceDescription.BusNumber = ConfigInfo->SystemIoBusNumber;
- DeviceDescription.DmaChannel = ConfigInfo->DmaChannel;
- DeviceDescription.InterfaceType = ConfigInfo->AdapterInterfaceType;
- DeviceDescription.DmaWidth = ConfigInfo->DmaWidth;
- DeviceDescription.DmaSpeed = ConfigInfo->DmaSpeed;
- DeviceDescription.MaximumLength = ConfigInfo->MaximumTransferLength;
- DeviceDescription.DmaPort = ConfigInfo->DmaPort;
-
- /* Get a DMA adapter object */
- DeviceExtension->AdapterObject = HalGetAdapter(&DeviceDescription,
- &DeviceExtension->MapRegisterCount);
- if (DeviceExtension->AdapterObject == NULL)
- {
- DPRINT1("HalGetAdapter() failed\n");
- return NULL;
- }
- }
-
- /* Allocate a common DMA buffer */
- DeviceExtension->CommonBufferLength =
- NumberOfBytes + DeviceExtension->SrbExtensionSize;
- DeviceExtension->VirtualAddress =
- HalAllocateCommonBuffer(DeviceExtension->AdapterObject,
- DeviceExtension->CommonBufferLength,
- &DeviceExtension->PhysicalAddress,
- FALSE);
- if (DeviceExtension->VirtualAddress == NULL)
- {
- DPRINT1("HalAllocateCommonBuffer() failed!\n");
- DeviceExtension->CommonBufferLength = 0;
- return NULL;
- }
-
- return (PVOID)((ULONG_PTR)DeviceExtension->VirtualAddress +
- DeviceExtension->SrbExtensionSize);
+ PSCSI_PORT_DEVICE_EXTENSION DeviceExtension;
+ DEVICE_DESCRIPTION DeviceDescription;
+ ULONG MapRegistersCount;
+ NTSTATUS Status;
+
+ DPRINT("ScsiPortGetUncachedExtension(%p %p %lu)\n",
+ HwDeviceExtension, ConfigInfo, NumberOfBytes);
+
+ DeviceExtension = CONTAINING_RECORD(HwDeviceExtension,
+ SCSI_PORT_DEVICE_EXTENSION,
+ MiniPortDeviceExtension);
+
+ /* Check for allocated common DMA buffer */
+ if (DeviceExtension->SrbExtensionBuffer != NULL)
+ {
+ DPRINT1("The HBA has already got a common DMA buffer!\n");
+ return NULL;
+ }
+
+ /* Check for DMA adapter object */
+ if (DeviceExtension->AdapterObject == NULL)
+ {
+ /* Initialize DMA adapter description */
+ RtlZeroMemory(&DeviceDescription, sizeof(DEVICE_DESCRIPTION));
+
+ DeviceDescription.Version = DEVICE_DESCRIPTION_VERSION;
+ DeviceDescription.Master = ConfigInfo->Master;
+ DeviceDescription.ScatterGather = ConfigInfo->ScatterGather;
+ DeviceDescription.DemandMode = ConfigInfo->DemandMode;
+ DeviceDescription.Dma32BitAddresses = ConfigInfo->Dma32BitAddresses;
+ DeviceDescription.BusNumber = ConfigInfo->SystemIoBusNumber;
+ DeviceDescription.DmaChannel = ConfigInfo->DmaChannel;
+ DeviceDescription.InterfaceType = ConfigInfo->AdapterInterfaceType;
+ DeviceDescription.DmaWidth = ConfigInfo->DmaWidth;
+ DeviceDescription.DmaSpeed = ConfigInfo->DmaSpeed;
+ DeviceDescription.MaximumLength = ConfigInfo->MaximumTransferLength;
+ DeviceDescription.DmaPort = ConfigInfo->DmaPort;
+
+ /* Get a DMA adapter object */
+ DeviceExtension->AdapterObject =
+ HalGetAdapter(&DeviceDescription, &MapRegistersCount);
+
+ /* Fail in case of error */
+ if (DeviceExtension->AdapterObject == NULL)
+ {
+ DPRINT1("HalGetAdapter() failed\n");
+ return NULL;
+ }
+
+ /* Set number of physical breaks */
+ if (ConfigInfo->NumberOfPhysicalBreaks != 0 &&
+ MapRegistersCount > ConfigInfo->NumberOfPhysicalBreaks)
+ {
+ DeviceExtension->PortCapabilities.MaximumPhysicalPages =
+ ConfigInfo->NumberOfPhysicalBreaks;
+ }
+ else
+ {
+ DeviceExtension->PortCapabilities.MaximumPhysicalPages =
MapRegistersCount;
+ }
+ }
+
+ /* Update auto request sense feature */
+ DeviceExtension->SupportsAutoSense = ConfigInfo->AutoRequestSense;
+
+ /* Update Srb extension size */
+ if (DeviceExtension->SrbExtensionSize != ConfigInfo->SrbExtensionSize)
+ DeviceExtension->SrbExtensionSize = ConfigInfo->SrbExtensionSize;
+
+ /* Update Srb extension alloc flag */
+ if (ConfigInfo->AutoRequestSense || DeviceExtension->SrbExtensionSize)
+ DeviceExtension->NeedSrbExtensionAlloc = TRUE;
+
+ /* Allocate a common DMA buffer */
+ Status = SpiAllocateCommonBuffer(DeviceExtension, NumberOfBytes);
+
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("SpiAllocateCommonBuffer() failed with Status = 0x%08X!\n",
Status);
+ return NULL;
+ }
+
+ return DeviceExtension->NonCachedExtension;
}
+
+static NTSTATUS
+SpiAllocateCommonBuffer(PSCSI_PORT_DEVICE_EXTENSION DeviceExtension, ULONG
NonCachedSize)
+{
+ PVOID *SrbExtension, CommonBuffer;
+ ULONG CommonBufferLength, BufSize;
+
+ /* If size is 0, set it to 16 */
+ if (!DeviceExtension->SrbExtensionSize)
+ DeviceExtension->SrbExtensionSize = 16;
+
+ /* Calculate size */
+ BufSize = DeviceExtension->SrbExtensionSize;
+
+ /* Add autosense data size if needed */
+ if (DeviceExtension->SupportsAutoSense)
+ BufSize += sizeof(SENSE_DATA);
+
+
+ /* Round it */
+ BufSize = (BufSize + sizeof(LONGLONG) - 1) & ~(sizeof(LONGLONG) - 1);
+
+ /* Sum up into the total common buffer length, and round it to page size */
+ CommonBufferLength =
+ ROUND_TO_PAGES(NonCachedSize + BufSize * DeviceExtension->RequestsNumber);
+
+ /* Allocate it */
+ if (!DeviceExtension->AdapterObject)
+ {
+ /* From nonpaged pool if there is no DMA */
+ CommonBuffer = ExAllocatePool(NonPagedPool, CommonBufferLength);
+ }
+ else
+ {
+ /* Perform a full request since we have a DMA adapter*/
+ CommonBuffer = HalAllocateCommonBuffer(DeviceExtension->AdapterObject,
+ CommonBufferLength,
+ &DeviceExtension->PhysicalAddress,
+ FALSE );
+ }
+
+ /* Fail in case of error */
+ if (!CommonBuffer)
+ return STATUS_INSUFFICIENT_RESOURCES;
+
+ /* Zero it */
+ RtlZeroMemory(CommonBuffer, CommonBufferLength);
+
+ /* Store its size in Device Extension */
+ DeviceExtension->CommonBufferLength = CommonBufferLength;
+
+ /* SrbExtension buffer is located at the beginning of the buffer */
+ DeviceExtension->SrbExtensionBuffer = CommonBuffer;
+
+ /* Non-cached extension buffer is located at the end of
+ the common buffer */
+ if (NonCachedSize)
+ {
+ CommonBufferLength -= NonCachedSize;
+ DeviceExtension->NonCachedExtension = (PUCHAR)CommonBuffer +
CommonBufferLength;
+ }
+ else
+ {
+ DeviceExtension->NonCachedExtension = NULL;
+ }
+
+ if (DeviceExtension->NeedSrbExtensionAlloc)
+ {
+ /* Look up how many SRB data structures we need */
+ DeviceExtension->SrbDataCount = CommonBufferLength / BufSize;
+
+ /* Initialize the free SRB extensions list */
+ SrbExtension = (PVOID *)CommonBuffer;
+ DeviceExtension->FreeSrbExtensions = SrbExtension;
+
+ /* Fill the remainding pointers (if we have more than 1 SRB) */
+ while (CommonBufferLength >= 2 * BufSize)
+ {
+ *SrbExtension = (PVOID*)((PCHAR)SrbExtension + BufSize);
+ SrbExtension = *SrbExtension;
+
+ CommonBufferLength -= BufSize;
+ }
+ }
+
+ return STATUS_SUCCESS;
+}
+
/*
@@ -1204,9 +1316,8 @@
DeviceExtension->SupportsAutoSense = PortConfig->AutoRequestSense;
DeviceExtension->NeedSrbExtensionAlloc = TRUE;
- //Status = STATUS_UNSUCCESFUL;
- /* TODO: Allocate common buffer */
- ASSERT(FALSE);
+ /* Allocate common buffer */
+ Status = SpiAllocateCommonBuffer(DeviceExtension, 0);
/* Check for failure */
if (!NT_SUCCESS(Status))