Author: fireball
Date: Sun Aug 15 08:48:03 2010
New Revision: 48551
URL: http://svn.reactos.org/svn/reactos?rev=48551&view=rev
Log:
[NTOSKRNL]
- Revert 48546. The code was correct, and there is more of same code in other places which firstly cancels the IRP and then moves to the next entry. The actual bug is somewhere else.
See issue #5550 for more details.
Modified:
trunk/reactos/ntoskrnl/io/iomgr/irp.c
Modified: trunk/reactos/ntoskrnl/io/iomgr/irp.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/io/iomgr/irp.c?re…
==============================================================================
--- trunk/reactos/ntoskrnl/io/iomgr/irp.c [iso-8859-1] (original)
+++ trunk/reactos/ntoskrnl/io/iomgr/irp.c [iso-8859-1] Sun Aug 15 08:48:03 2010
@@ -1047,12 +1047,14 @@
NextEntry = ListHead->Flink;
while (ListHead != NextEntry)
{
- /* Get the IRP and move to the next entry */
+ /* Get the IRP */
Irp = CONTAINING_RECORD(NextEntry, IRP, ThreadListEntry);
- NextEntry = NextEntry->Flink;
/* Cancel it */
IoCancelIrp(Irp);
+
+ /* Move to the next entry */
+ NextEntry = NextEntry->Flink;
}
/* Wait 100 milliseconds */
Author: evb
Date: Sat Aug 14 17:33:10 2010
New Revision: 48549
URL: http://svn.reactos.org/svn/reactos?rev=48549&view=rev
Log:
- IRP_MN_QUERY_RESOURCES support for PDO (PciQueryResources, PciAllocateCmResourceList), now remain IRP_MN_QUERY_RESOURCE_REQUIREMENTS to last device stack interogration from PNPMGR
Modified:
trunk/reactos/drivers/bus/pcix/enum.c
trunk/reactos/drivers/bus/pcix/utils.c
Modified: trunk/reactos/drivers/bus/pcix/enum.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/bus/pcix/enum.c?re…
==============================================================================
--- trunk/reactos/drivers/bus/pcix/enum.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/bus/pcix/enum.c [iso-8859-1] Sat Aug 14 17:33:10 2010
@@ -49,14 +49,190 @@
/* FUNCTIONS ******************************************************************/
+PCM_RESOURCE_LIST
+NTAPI
+PciAllocateCmResourceList(IN ULONG Count,
+ IN ULONG BusNumber)
+{
+ SIZE_T Size;
+ PCM_RESOURCE_LIST ResourceList;
+
+ /* Calculate the final size of the list, including each descriptor */
+ Size = sizeof(CM_RESOURCE_LIST);
+ if (Count > 1) Size = sizeof(CM_PARTIAL_RESOURCE_DESCRIPTOR) * (Count - 1) +
+ sizeof(CM_RESOURCE_LIST);
+
+ /* Allocate the list */
+ ResourceList = ExAllocatePoolWithTag(PagedPool, Size, 'BicP');
+ if (!ResourceList) return NULL;
+
+ /* Initialize it */
+ RtlZeroMemory(ResourceList, Size);
+ ResourceList->Count = 1;
+ ResourceList->List[0].BusNumber = BusNumber;
+ ResourceList->List[0].InterfaceType = PCIBus;
+ ResourceList->List[0].PartialResourceList.Version = 1;
+ ResourceList->List[0].PartialResourceList.Revision = 1;
+ ResourceList->List[0].PartialResourceList.Count = Count;
+
+ /* Return it */
+ return ResourceList;
+}
+
NTSTATUS
NTAPI
PciQueryResources(IN PPCI_PDO_EXTENSION PdoExtension,
OUT PCM_RESOURCE_LIST *Buffer)
{
- /* Not yet implemented */
- UNIMPLEMENTED;
- while (TRUE);
+ PPCI_FUNCTION_RESOURCES PciResources;
+ BOOLEAN HaveVga, HaveMemSpace, HaveIoSpace;
+ USHORT BridgeControl, PciCommand;
+ ULONG Count, i;
+ PCM_PARTIAL_RESOURCE_DESCRIPTOR Partial, Resource, LastResource;
+ PCM_RESOURCE_LIST ResourceList;
+ UCHAR InterruptLine;
+ PAGED_CODE();
+
+ /* Assume failure */
+ Count = 0;
+ HaveVga = FALSE;
+ *Buffer = NULL;
+
+ /* Make sure there's some resources to query */
+ PciResources = PdoExtension->Resources;
+ if (!PciResources) return STATUS_SUCCESS;
+
+ /* Read the decodes */
+ PciReadDeviceConfig(PdoExtension,
+ &PciCommand,
+ FIELD_OFFSET(PCI_COMMON_HEADER, Command),
+ sizeof(USHORT));
+
+ /* Check which ones are turned on */
+ HaveIoSpace = PciCommand & PCI_ENABLE_IO_SPACE;
+ HaveMemSpace = PciCommand & PCI_ENABLE_MEMORY_SPACE;
+
+ /* Loop maximum possible descriptors */
+ for (i = 0; i < 7; i++)
+ {
+ /* Check if the decode for this descriptor is actually turned on */
+ Partial = &PciResources->Current[i];
+ if (((HaveMemSpace) && (Partial->Type == CmResourceTypeMemory)) ||
+ ((HaveIoSpace) && (Partial->Type == CmResourceTypePort)))
+ {
+ /* One more fully active descriptor */
+ Count++;
+ }
+ }
+
+ /* If there's an interrupt pin associated, check at least one decode is on */
+ if ((PdoExtension->InterruptPin) && ((HaveMemSpace) || (HaveIoSpace)))
+ {
+ /* Read the interrupt line for the pin, add a descriptor if it's valid */
+ InterruptLine = PdoExtension->AdjustedInterruptLine;
+ if ((InterruptLine) && (InterruptLine != -1)) Count++;
+ }
+
+ /* Check for PCI bridge */
+ if (PdoExtension->HeaderType == PCI_BRIDGE_TYPE)
+ {
+ /* Read bridge settings, check if VGA is present */
+ PciReadDeviceConfig(PdoExtension,
+ &BridgeControl,
+ FIELD_OFFSET(PCI_COMMON_HEADER, u.type1.BridgeControl),
+ sizeof(USHORT));
+ if (BridgeControl & PCI_ENABLE_BRIDGE_VGA)
+ {
+ /* Remember for later */
+ HaveVga = TRUE;
+
+ /* One memory descriptor for 0xA0000, plus the two I/O port ranges */
+ if (HaveMemSpace) Count++;
+ if (HaveIoSpace) Count += 2;
+ }
+ }
+
+ /* If there's no descriptors in use, there's no resources, so return */
+ if (!Count) return STATUS_SUCCESS;
+
+ /* Allocate a resource list to hold the resources */
+ ResourceList = PciAllocateCmResourceList(Count,
+ PdoExtension->ParentFdoExtension->BaseBus);
+ if (!ResourceList) return STATUS_INSUFFICIENT_RESOURCES;
+
+ /* This is where the descriptors will be copied into */
+ Resource = ResourceList->List[0].PartialResourceList.PartialDescriptors;
+ LastResource = Resource + Count + 1;
+
+ /* Loop maximum possible descriptors */
+ for (i = 0; i < 7; i++)
+ {
+ /* Check if the decode for this descriptor is actually turned on */
+ Partial = &PciResources->Current[i];
+ if (((HaveMemSpace) && (Partial->Type == CmResourceTypeMemory)) ||
+ ((HaveIoSpace) && (Partial->Type == CmResourceTypePort)))
+ {
+ /* Copy the descriptor into the resource list */
+ *Resource++ = *Partial;
+ }
+ }
+
+ /* Check if earlier the code detected this was a PCI bridge with VGA on it */
+ if (HaveVga)
+ {
+ /* Are the memory decodes enabled? */
+ if (HaveMemSpace)
+ {
+ /* Build a memory descriptor for a 128KB framebuffer at 0xA0000 */
+ Resource->Flags = CM_RESOURCE_MEMORY_READ_WRITE;
+ Resource->u.Generic.Start.HighPart = 0;
+ Resource->Type = CmResourceTypeMemory;
+ Resource->u.Generic.Start.LowPart = 0xA0000;
+ Resource->u.Generic.Length = 0x20000;
+ Resource++;
+ }
+
+ /* Are the I/O decodes enabled? */
+ if (HaveIoSpace)
+ {
+ /* Build an I/O descriptor for the graphic ports at 0x3B0 */
+ Resource->Type = CmResourceTypePort;
+ Resource->Flags = CM_RESOURCE_PORT_POSITIVE_DECODE | CM_RESOURCE_PORT_10_BIT_DECODE;
+ Resource->u.Port.Start.QuadPart = 0x3B0u;
+ Resource->u.Port.Length = 0xC;
+ Resource++;
+
+ /* Build an I/O descriptor for the graphic ports at 0x3C0 */
+ Resource->Type = CmResourceTypePort;
+ Resource->Flags = CM_RESOURCE_PORT_POSITIVE_DECODE | CM_RESOURCE_PORT_10_BIT_DECODE;
+ Resource->u.Port.Start.QuadPart = 0x3C0u;
+ Resource->u.Port.Length = 0x20;
+ Resource++;
+ }
+ }
+
+ /* If there's an interrupt pin associated, check at least one decode is on */
+ if ((PdoExtension->InterruptPin) && ((HaveMemSpace) || (HaveIoSpace)))
+ {
+ /* Read the interrupt line for the pin, check if it's valid */
+ InterruptLine = PdoExtension->AdjustedInterruptLine;
+ if ((InterruptLine) && (InterruptLine != -1))
+ {
+ /* Make sure there's still space */
+ ASSERT(Resource < LastResource);
+
+ /* Add the interrupt descriptor */
+ Resource->Flags = CM_RESOURCE_INTERRUPT_LEVEL_SENSITIVE;
+ Resource->Type = CmResourceTypeInterrupt;
+ Resource->ShareDisposition = CmResourceShareShared;
+ Resource->u.Interrupt.Affinity = -1;
+ Resource->u.Interrupt.Level = InterruptLine;
+ Resource->u.Interrupt.Vector = InterruptLine;
+ }
+ }
+
+ /* Return the resouce list */
+ *Buffer = ResourceList;
return STATUS_SUCCESS;
}
Modified: trunk/reactos/drivers/bus/pcix/utils.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/bus/pcix/utils.c?r…
==============================================================================
--- trunk/reactos/drivers/bus/pcix/utils.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/bus/pcix/utils.c [iso-8859-1] Sat Aug 14 17:33:10 2010
@@ -1355,7 +1355,7 @@
SlotInfo->BusNumber,
SlotInfo->DeviceNumber,
SlotInfo->SlotNumber);
-
+
/* Check if this slot information matches the PDO being queried */
if ((ParentExtension->BaseBus == SlotInfo->BusNumber) &&
(PdoExtension->Slot.u.bits.DeviceNumber == SlotInfo->DeviceNumber >> 3) &&
@@ -1365,7 +1365,7 @@
*SlotNumber = SlotInfo->SlotNumber;
return STATUS_SUCCESS;
}
-
+
/* Try the next slot */
SlotInfo++;
}
@@ -1475,7 +1475,7 @@
DEVICE_CAPABILITIES AttachedCaps;
DEVICE_POWER_STATE NewPowerState, DevicePowerState, DeviceWakeLevel, DeviceWakeState;
SYSTEM_POWER_STATE SystemWakeState, DeepestWakeState, CurrentState;
-
+
/* Nothing is known at first */
DeviceWakeState = PowerDeviceUnspecified;
SystemWakeState = DeepestWakeState = PowerSystemUnspecified;
@@ -1523,7 +1523,7 @@
sizeof(DeviceCapability->DeviceState));
return STATUS_SUCCESS;
}
-
+
/* The PCI Device has power capabilities, so read which ones are supported */
DeviceCapability->DeviceD1 = PdoExtension->PowerCapabilities.Support.D1;
DeviceCapability->DeviceD2 = PdoExtension->PowerCapabilities.Support.D2;
@@ -1560,7 +1560,7 @@
/* Read the current mapping from the attached device */
DevicePowerState = AttachedCaps.DeviceState[CurrentState];
NewPowerState = DevicePowerState;
-
+
/* The attachee suports D1, but this PDO does not */
if ((NewPowerState == PowerDeviceD1) &&
!(PdoExtension->PowerCapabilities.Support.D1))
@@ -1568,7 +1568,7 @@
/* Fall back to D2 */
NewPowerState = PowerDeviceD2;
}
-
+
/* The attachee supports D2, but this PDO does not */
if ((NewPowerState == PowerDeviceD2) &&
!(PdoExtension->PowerCapabilities.Support.D2))
@@ -1576,10 +1576,10 @@
/* Fall back to D3 */
NewPowerState = PowerDeviceD3;
}
-
+
/* Set the mapping based on the best state supported */
DeviceCapability->DeviceState[CurrentState] = NewPowerState;
-
+
/* Check if sleep states are being processed, and a mapping was found */
if ((CurrentState < PowerSystemHibernate) &&
(NewPowerState != PowerDeviceUnspecified))
@@ -1587,8 +1587,8 @@
/* Save this state as being the deepest one found until now */
DeepestWakeState = CurrentState;
}
-
- /*
+
+ /*
* Finally, check if the computed sleep state is within the states that
* this device can wake the system from, and if it's higher or equal to
* the sleep state mapping that came from the attachee, assuming that it
@@ -1618,10 +1618,10 @@
DeviceWakeState = NewPowerState;
}
}
-
+
/* Read the current wake level */
DeviceWakeLevel = PdoExtension->PowerState.DeviceWakeLevel;
-
+
/* Check if the attachee's wake levels are valid, and the PDO's is higher */
if ((AttachedCaps.SystemWake != PowerSystemUnspecified) &&
(AttachedCaps.DeviceWake != PowerDeviceUnspecified) &&
@@ -1639,7 +1639,7 @@
/* Bump to D1 */
DeviceCapability->DeviceWake = PowerDeviceD1;
}
-
+
/* Now check if the wake level is D1, but the PDO doesn't support it */
if ((DeviceCapability->DeviceWake == PowerDeviceD1) &&
!(DeviceCapability->WakeFromD1))
@@ -1647,7 +1647,7 @@
/* Bump to D2 */
DeviceCapability->DeviceWake = PowerDeviceD2;
}
-
+
/* Now check if the wake level is D2, but the PDO doesn't support it */
if ((DeviceCapability->DeviceWake == PowerDeviceD2) &&
!(DeviceCapability->WakeFromD2))
@@ -1655,7 +1655,7 @@
/* Bump it to D3 */
DeviceCapability->DeviceWake = PowerDeviceD3;
}
-
+
/* Now check if the wake level is D3, but the PDO doesn't support it */
if ((DeviceCapability->DeviceWake == PowerDeviceD3) &&
!(DeviceCapability->WakeFromD3))
@@ -1676,12 +1676,12 @@
/* Use the wake state that had been computed earlier */
DeviceCapability->DeviceWake = DeviceWakeState;
DeviceCapability->SystemWake = SystemWakeState;
-
+
/* If that state was D3, then the device supports Hot/Cold D3 */
if (DeviceWakeState == PowerDeviceD3) DeviceCapability->WakeFromD3 = TRUE;
}
}
-
+
/*
* Finally, check for off states (lower than S3, such as hibernate) and
* make sure that the device both supports waking from D3 as well as
@@ -1694,12 +1694,12 @@
/* It doesn't, so pick the computed lowest wake state from earlier */
DeviceCapability->SystemWake = DeepestWakeState;
}
-
+
/* Set the PCI Specification mandated maximum latencies for transitions */
DeviceCapability->D1Latency = 0;
DeviceCapability->D2Latency = 2;
DeviceCapability->D3Latency = 100;
-
+
/* Sanity check */
ASSERT(DeviceCapability->DeviceState[PowerSystemWorking] == PowerDeviceD0);
}
@@ -1710,7 +1710,7 @@
DeviceCapability->D2Latency = 0;
DeviceCapability->D3Latency = 0;
}
-
+
/* This function always succeeds, even without power management support */
return STATUS_SUCCESS;
}
Author: evb
Date: Sat Aug 14 17:09:20 2010
New Revision: 48548
URL: http://svn.reactos.org/svn/reactos?rev=48548&view=rev
Log:
- Add support for PnP IRP to PDO: IRP_MN_QUERY_BUS_INFORMATION (PciQueryBusInformation), IRP_MN_QUERY_ID (PciQueryId), IRP_MN_QUERY_DEVICE_TEXT (PciQueryDeviceText), IRP_MN_QUERY_CAPABILITIES (PciQueryCapabilities), IRP_MN_QUERY_DEVICE_RELATIONS (PciQueryTargetDeviceRelations implement, PciQueryEjectionRelations, stub)
- Stub support for PnP IRP to PDO: IRP_MN_QUERY_RESOURCE_REQUIREMENTS (PciQueryRequirements), IRP_MN_QUERY_RESOURCES(PciQueryResources)
- Add support for PnP IRP to FDO: IRP_MN_QUERY_CAPABILITIES (handle in PciFdoIrpQueryDeviceCapabilities)
- Build device capability UI number (PciDetermineSlotNumber), use PIR$ (seem support broken, need to check loader) or device property for bus not root
- Use parent attachee device and this PDO for build device/system wake states, latency, device/system power mappings
- PCI-ID manage support: PciInitIdBuffer, PciIdPrintf, PciIdPrintfAppend
- Debug helper: PciDebugDumpQueryCapabilities
- Thanks richard for advise + beer
PCI-X driver now pass 10000 codes lines!
Modified:
trunk/reactos/drivers/bus/pcix/debug.c
trunk/reactos/drivers/bus/pcix/enum.c
trunk/reactos/drivers/bus/pcix/fdo.c
trunk/reactos/drivers/bus/pcix/pci.h
trunk/reactos/drivers/bus/pcix/pci/id.c
trunk/reactos/drivers/bus/pcix/pdo.c
trunk/reactos/drivers/bus/pcix/utils.c
Modified: trunk/reactos/drivers/bus/pcix/debug.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/bus/pcix/debug.c?r…
==============================================================================
--- trunk/reactos/drivers/bus/pcix/debug.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/bus/pcix/debug.c [iso-8859-1] Sat Aug 14 17:09:20 2010
@@ -49,6 +49,26 @@
"QUERY_POWER",
};
+PCHAR SystemPowerStates[] =
+{
+ "Unspecified",
+ "Working",
+ "Sleeping1",
+ "Sleeping2",
+ "Sleeping3",
+ "Hibernate",
+ "Shutdown"
+};
+
+PCHAR DevicePowerStates[] =
+{
+ "Unspecified",
+ "D0",
+ "D1",
+ "D2",
+ "D3"
+};
+
ULONG PciBreakOnPdoPowerIrp, PciBreakOnFdoPowerIrp;
ULONG PciBreakOnPdoPnpIrp, PciBreakOnFdoPnpIrp;
@@ -194,4 +214,41 @@
}
}
+VOID
+NTAPI
+PciDebugDumpQueryCapabilities(IN PDEVICE_CAPABILITIES DeviceCaps)
+{
+ ULONG i;
+
+ /* Dump the capabilities */
+ DPRINT1("Capabilities\n Lock:%d, Eject:%d, Remove:%d, Dock:%d, UniqueId:%d\n",
+ DeviceCaps->LockSupported,
+ DeviceCaps->EjectSupported,
+ DeviceCaps->Removable,
+ DeviceCaps->DockDevice,
+ DeviceCaps->UniqueID);
+ DbgPrint(" SilentInstall:%d, RawOk:%d, SurpriseOk:%d\n",
+ DeviceCaps->SilentInstall,
+ DeviceCaps->RawDeviceOK,
+ DeviceCaps->SurpriseRemovalOK);
+ DbgPrint(" Address %08x, UINumber %08x, Latencies D1 %d, D2 %d, D3 %d\n",
+ DeviceCaps->Address,
+ DeviceCaps->UINumber,
+ DeviceCaps->D1Latency,
+ DeviceCaps->D2Latency,
+ DeviceCaps->D3Latency);
+
+ /* Dump and convert the wake levels */
+ DbgPrint(" System Wake: %s, Device Wake: %s\n DeviceState[PowerState] [",
+ SystemPowerStates[min(DeviceCaps->SystemWake, PowerSystemMaximum)],
+ DevicePowerStates[min(DeviceCaps->DeviceWake, PowerDeviceMaximum)]);
+
+ /* Dump and convert the power state mappings */
+ for (i = PowerSystemWorking; i < PowerSystemMaximum; i++)
+ DbgPrint(" %s", DevicePowerStates[DeviceCaps->DeviceState[i]]);
+
+ /* Finish the dump */
+ DbgPrint(" ]\n");
+}
+
/* EOF */
Modified: trunk/reactos/drivers/bus/pcix/enum.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/bus/pcix/enum.c?re…
==============================================================================
--- trunk/reactos/drivers/bus/pcix/enum.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/bus/pcix/enum.c [iso-8859-1] Sat Aug 14 17:09:20 2010
@@ -13,6 +13,8 @@
#include <debug.h>
/* GLOBALS ********************************************************************/
+
+PIO_RESOURCE_REQUIREMENTS_LIST PciZeroIoResourceRequirements;
PCI_CONFIGURATOR PciConfigurators[] =
{
@@ -46,6 +48,65 @@
};
/* FUNCTIONS ******************************************************************/
+
+NTSTATUS
+NTAPI
+PciQueryResources(IN PPCI_PDO_EXTENSION PdoExtension,
+ OUT PCM_RESOURCE_LIST *Buffer)
+{
+ /* Not yet implemented */
+ UNIMPLEMENTED;
+ while (TRUE);
+ return STATUS_SUCCESS;
+}
+
+NTSTATUS
+NTAPI
+PciQueryTargetDeviceRelations(IN PPCI_PDO_EXTENSION PdoExtension,
+ IN OUT PDEVICE_RELATIONS *pDeviceRelations)
+{
+ PDEVICE_RELATIONS DeviceRelations;
+ PAGED_CODE();
+
+ /* If there were existing relations, free them */
+ if (*pDeviceRelations) ExFreePoolWithTag(*pDeviceRelations, 0);
+
+ /* Allocate a new structure for the relations */
+ DeviceRelations = ExAllocatePoolWithTag(NonPagedPool,
+ sizeof(DEVICE_RELATIONS),
+ 'BicP');
+ if (!DeviceRelations) return STATUS_INSUFFICIENT_RESOURCES;
+
+ /* Only one relation: the PDO */
+ DeviceRelations->Count = 1;
+ DeviceRelations->Objects[0] = PdoExtension->PhysicalDeviceObject;
+ ObReferenceObject(DeviceRelations->Objects[0]);
+
+ /* Return the new relations */
+ *pDeviceRelations = DeviceRelations;
+ return STATUS_SUCCESS;
+}
+
+NTSTATUS
+NTAPI
+PciQueryEjectionRelations(IN PPCI_PDO_EXTENSION PdoExtension,
+ IN OUT PDEVICE_RELATIONS *pDeviceRelations)
+{
+ /* Not yet implemented */
+ UNIMPLEMENTED;
+ while (TRUE);
+}
+
+NTSTATUS
+NTAPI
+PciQueryRequirements(IN PPCI_PDO_EXTENSION PdoExtension,
+ IN OUT PIO_RESOURCE_REQUIREMENTS_LIST *RequirementsList)
+{
+ /* Not yet implemented */
+ UNIMPLEMENTED;
+ while (TRUE);
+ return STATUS_SUCCESS;
+}
/*
* 7. The IO/MEM/Busmaster decodes are disabled for the device.
Modified: trunk/reactos/drivers/bus/pcix/fdo.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/bus/pcix/fdo.c?rev…
==============================================================================
--- trunk/reactos/drivers/bus/pcix/fdo.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/bus/pcix/fdo.c [iso-8859-1] Sat Aug 14 17:09:20 2010
@@ -295,9 +295,23 @@
IN PIO_STACK_LOCATION IoStackLocation,
IN PPCI_FDO_EXTENSION DeviceExtension)
{
- UNIMPLEMENTED;
- while (TRUE);
- return STATUS_NOT_SUPPORTED;
+ PDEVICE_CAPABILITIES Capabilities;
+ PAGED_CODE();
+ ASSERT_FDO(DeviceExtension);
+
+ /* Get the capabilities */
+ Capabilities = IoStackLocation->Parameters.DeviceCapabilities.Capabilities;
+
+ /* Inherit wake levels and power mappings from the higher-up capabilities */
+ DeviceExtension->PowerState.SystemWakeLevel = Capabilities->SystemWake;
+ DeviceExtension->PowerState.DeviceWakeLevel = Capabilities->DeviceWake;
+ RtlCopyMemory(DeviceExtension->PowerState.SystemStateMapping,
+ Capabilities->DeviceState,
+ sizeof(DeviceExtension->PowerState.SystemStateMapping));
+
+ /* Dump the capabilities and return success */
+ PciDebugDumpQueryCapabilities(Capabilities);
+ return STATUS_SUCCESS;
}
NTSTATUS
Modified: trunk/reactos/drivers/bus/pcix/pci.h
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/bus/pcix/pci.h?rev…
==============================================================================
--- trunk/reactos/drivers/bus/pcix/pci.h [iso-8859-1] (original)
+++ trunk/reactos/drivers/bus/pcix/pci.h [iso-8859-1] Sat Aug 14 17:09:20 2010
@@ -78,6 +78,11 @@
// PCI Driver Verifier Failures
//
#define PCI_VERIFIER_CODES 0x04
+
+//
+// PCI ID Buffer ANSI Strings
+//
+#define MAX_ANSI_STRINGS 0x08
//
// Device Extension, Interface, Translator and Arbiter Signatures
@@ -411,6 +416,19 @@
} PCI_VERIFIER_DATA, *PPCI_VERIFIER_DATA;
//
+// PCI ID Buffer Descriptor
+//
+typedef struct _PCI_ID_BUFFER
+{
+ ULONG Count;
+ ANSI_STRING Strings[MAX_ANSI_STRINGS];
+ ULONG StringSize[MAX_ANSI_STRINGS];
+ ULONG TotalLength;
+ PCHAR CharBuffer;
+ CHAR BufferData[256];
+} PCI_ID_BUFFER, *PPCI_ID_BUFFER;
+
+//
// PCI Configuration Callbacks
//
struct _PCI_CONFIGURATOR_CONTEXT;
@@ -1111,6 +1129,20 @@
OUT PUSHORT Command
);
+NTSTATUS
+NTAPI
+PciQueryBusInformation(
+ IN PPCI_PDO_EXTENSION PdoExtension,
+ IN PPNP_BUS_INFORMATION* Buffer
+);
+
+NTSTATUS
+NTAPI
+PciQueryCapabilities(
+ IN PPCI_PDO_EXTENSION PdoExtension,
+ IN OUT PDEVICE_CAPABILITIES DeviceCapability
+);
+
//
// Configuration Routines
//
@@ -1215,6 +1247,12 @@
NTAPI
PciDebugDumpCommonConfig(
IN PPCI_COMMON_HEADER PciData
+);
+
+VOID
+NTAPI
+PciDebugDumpQueryCapabilities(
+ IN PDEVICE_CAPABILITIES DeviceCaps
);
//
@@ -1452,6 +1490,34 @@
IN OUT PDEVICE_RELATIONS *pDeviceRelations
);
+NTSTATUS
+NTAPI
+PciQueryResources(
+ IN PPCI_PDO_EXTENSION PdoExtension,
+ OUT PCM_RESOURCE_LIST *Buffer
+);
+
+NTSTATUS
+NTAPI
+PciQueryTargetDeviceRelations(
+ IN PPCI_PDO_EXTENSION PdoExtension,
+ IN OUT PDEVICE_RELATIONS *pDeviceRelations
+);
+
+NTSTATUS
+NTAPI
+PciQueryEjectionRelations(
+ IN PPCI_PDO_EXTENSION PdoExtension,
+ IN OUT PDEVICE_RELATIONS *pDeviceRelations
+);
+
+NTSTATUS
+NTAPI
+PciQueryRequirements(
+ IN PPCI_PDO_EXTENSION PdoExtension,
+ IN OUT PIO_RESOURCE_REQUIREMENTS_LIST *RequirementsList
+);
+
//
// Identification Functions
//
@@ -1460,6 +1526,23 @@
PciGetDeviceDescriptionMessage(
IN UCHAR BaseClass,
IN UCHAR SubClass
+);
+
+NTSTATUS
+NTAPI
+PciQueryDeviceText(
+ IN PPCI_PDO_EXTENSION PdoExtension,
+ IN DEVICE_TEXT_TYPE QueryType,
+ IN ULONG Locale,
+ OUT PWCHAR *Buffer
+);
+
+NTSTATUS
+NTAPI
+PciQueryId(
+ IN PPCI_PDO_EXTENSION DeviceExtension,
+ IN BUS_QUERY_ID_TYPE QueryType,
+ OUT PWCHAR *Buffer
);
//
@@ -1627,6 +1710,8 @@
extern PPCI_HACK_ENTRY PciHackTable;
extern BOOLEAN PciAssignBusNumbers;
extern BOOLEAN PciEnableNativeModeATA;
+extern PPCI_IRQ_ROUTING_TABLE PciIrqRoutingTable;
+extern BOOLEAN PciRunningDatacenter;
/* Exported by NTOS, should this go in the NDK? */
extern NTSYSAPI BOOLEAN InitSafeBootMode;
Modified: trunk/reactos/drivers/bus/pcix/pci/id.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/bus/pcix/pci/id.c?…
==============================================================================
--- trunk/reactos/drivers/bus/pcix/pci/id.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/bus/pcix/pci/id.c [iso-8859-1] Sat Aug 14 17:09:20 2010
@@ -11,6 +11,7 @@
#include <pci.h>
#define NDEBUG
#include <debug.h>
+#include "stdio.h"
/* GLOBALS ********************************************************************/
@@ -107,4 +108,354 @@
return Message;
}
+VOID
+NTAPI
+PciInitIdBuffer(IN PPCI_ID_BUFFER IdBuffer)
+{
+ /* Initialize the sizes to zero and the pointer to the start of the buffer */
+ IdBuffer->TotalLength = 0;
+ IdBuffer->Count = 0;
+ IdBuffer->CharBuffer = IdBuffer->BufferData;
+}
+
+ULONG
+NTAPI
+PciIdPrintf(IN PPCI_ID_BUFFER IdBuffer,
+ IN PCCH Format,
+ ...)
+{
+ ULONG Size, Length;
+ PANSI_STRING AnsiString;
+ va_list va;
+ va_start(va, Format);
+ ASSERT(IdBuffer->Count < MAX_ANSI_STRINGS);
+
+ /* Do the actual string formatting into the character buffer */
+ vsprintf(IdBuffer->CharBuffer, Format, va);
+
+ /* Initialize the ANSI_STRING that will hold this string buffer */
+ AnsiString = &IdBuffer->Strings[IdBuffer->Count];
+ RtlInitAnsiString(AnsiString, IdBuffer->CharBuffer);
+
+ /* Calculate the final size of the string, in Unicode */
+ Size = RtlAnsiStringToUnicodeSize(AnsiString);
+
+ /* Update hte buffer with the size,and update the character pointer */
+ IdBuffer->StringSize[IdBuffer->Count] = Size;
+ IdBuffer->TotalLength += Size;
+ Length = AnsiString->Length + sizeof(ANSI_NULL);
+ IdBuffer->CharBuffer += Length;
+
+ /* Move to the next string for next time */
+ IdBuffer->Count++;
+
+ /* Return the length */
+ return Length;
+}
+
+ULONG
+NTAPI
+PciIdPrintfAppend(IN PPCI_ID_BUFFER IdBuffer,
+ IN PCCH Format,
+ ...)
+{
+ ULONG NextId, Size, Length, MaxLength;
+ PANSI_STRING AnsiString;
+ va_list va;
+ va_start(va, Format);
+ ASSERT(IdBuffer->Count);
+
+ /* Choose the next static ANSI_STRING to use */
+ NextId = IdBuffer->Count - 1;
+
+ /* Max length is from the end of the buffer up until the current pointer */
+ MaxLength = (PCHAR)(IdBuffer + 1) - IdBuffer->CharBuffer;
+
+ /* Do the actual append, and return the length this string took */
+ Length = vsprintf(IdBuffer->CharBuffer - 1, Format, va);
+ ASSERT(Length < MaxLength);
+
+ /* Select the static ANSI_STRING, and update its length information */
+ AnsiString = &IdBuffer->Strings[NextId];
+ AnsiString->Length += Length;
+ AnsiString->MaximumLength += Length;
+
+ /* Calculate the final size of the string, in Unicode */
+ Size = RtlAnsiStringToUnicodeSize(AnsiString);
+
+ /* Update the buffer with the size, and update the character pointer */
+ IdBuffer->StringSize[NextId] = Size;
+ IdBuffer->TotalLength += Size;
+ IdBuffer->CharBuffer += Length;
+
+ /* Return the size */
+ return Size;
+}
+
+NTSTATUS
+NTAPI
+PciQueryId(IN PPCI_PDO_EXTENSION DeviceExtension,
+ IN BUS_QUERY_ID_TYPE QueryType,
+ OUT PWCHAR *Buffer)
+{
+ ULONG SubsysId;
+ CHAR VendorString[22];
+ PPCI_PDO_EXTENSION PdoExtension;
+ PPCI_FDO_EXTENSION ParentExtension;
+ PWCHAR StringBuffer;
+ ULONG i, Size;
+ NTSTATUS Status;
+ PANSI_STRING NextString;
+ UNICODE_STRING DestinationString;
+ PCI_ID_BUFFER IdBuffer;
+ PAGED_CODE();
+
+ /* Assume failure */
+ Status = STATUS_SUCCESS;
+ *Buffer = NULL;
+
+ /* Start with the genric vendor string, which is the vendor ID + device ID */
+ sprintf(VendorString,
+ "PCI\\VEN_%04X&DEV_%04X",
+ DeviceExtension->VendorId,
+ DeviceExtension->DeviceId);
+
+ /* Initialize the PCI ID Buffer */
+ PciInitIdBuffer(&IdBuffer);
+
+ /* Build the subsystem ID as shown in PCI ID Strings */
+ SubsysId = DeviceExtension->SubsystemVendorId | (DeviceExtension->SubsystemId << 16);
+
+ /* Check what the caller is requesting */
+ switch (QueryType)
+ {
+ case BusQueryDeviceID:
+
+ /* A single ID, the vendor string + the revision ID */
+ PciIdPrintf(&IdBuffer,
+ "%s&SUBSYS_%08X&REV_%02X",
+ VendorString,
+ SubsysId,
+ DeviceExtension->RevisionId);
+ break;
+
+ case BusQueryHardwareIDs:
+
+ /* First the vendor string + the subsystem ID + the revision ID */
+ PciIdPrintf(&IdBuffer,
+ "%s&SUBSYS_%08X&REV_%02X",
+ VendorString,
+ SubsysId,
+ DeviceExtension->RevisionId);
+
+ /* Next, without the revision */
+ PciIdPrintf(&IdBuffer,
+ "%s&SUBSYS_%08X",
+ VendorString,
+ SubsysId);
+
+ /* Next, the vendor string + the base class + sub class + progif */
+ PciIdPrintf(&IdBuffer,
+ "%s&CC_%02X%02X%02X",
+ VendorString,
+ DeviceExtension->BaseClass,
+ DeviceExtension->SubClass,
+ DeviceExtension->ProgIf);
+
+ /* Next, without the progif */
+ PciIdPrintf(&IdBuffer,
+ "%s&CC_%02X%02X",
+ VendorString,
+ DeviceExtension->BaseClass,
+ DeviceExtension->SubClass);
+
+ /* And finally, a terminator */
+ PciIdPrintf(&IdBuffer, "\0");
+ break;
+
+ case BusQueryCompatibleIDs:
+
+ /* First, the vendor + revision ID only */
+ PciIdPrintf(&IdBuffer,
+ "%s&REV_%02X",
+ VendorString,
+ DeviceExtension->RevisionId);
+
+ /* Next, the vendor string alone */
+ PciIdPrintf(&IdBuffer, "%s", VendorString);
+
+ /* Next, the vendor ID + the base class + the sub class + progif */
+ PciIdPrintf(&IdBuffer,
+ "PCI\\VEN_%04X&CC_%02X%02X%02X",
+ DeviceExtension->VendorId,
+ DeviceExtension->BaseClass,
+ DeviceExtension->SubClass,
+ DeviceExtension->ProgIf);
+
+ /* Now without the progif */
+ PciIdPrintf(&IdBuffer,
+ "PCI\\VEN_%04X&CC_%02X%02X",
+ DeviceExtension->VendorId,
+ DeviceExtension->BaseClass,
+ DeviceExtension->SubClass);
+
+ /* And then just the vendor ID itself */
+ PciIdPrintf(&IdBuffer,
+ "PCI\\VEN_%04X",
+ DeviceExtension->VendorId);
+
+ /* Then the base class + subclass + progif, without any vendor */
+ PciIdPrintf(&IdBuffer,
+ "PCI\\CC_%02X%02X%02X",
+ DeviceExtension->BaseClass,
+ DeviceExtension->SubClass,
+ DeviceExtension->ProgIf);
+
+ /* Next, without the progif */
+ PciIdPrintf(&IdBuffer,
+ "PCI\\CC_%02X%02X",
+ DeviceExtension->BaseClass,
+ DeviceExtension->SubClass);
+
+ /* And finally, a terminator */
+ PciIdPrintf(&IdBuffer, "\0");
+ break;
+
+ case BusQueryInstanceID:
+
+ /* Start with a terminator */
+ PciIdPrintf(&IdBuffer, "\0");
+
+ /* And then encode the device and function number */
+ PciIdPrintfAppend(&IdBuffer,
+ "%02X",
+ (DeviceExtension->Slot.u.bits.DeviceNumber << 3) |
+ DeviceExtension->Slot.u.bits.FunctionNumber);
+
+ /* Loop every parent until the root */
+ ParentExtension = DeviceExtension->ParentFdoExtension;
+ while (!PCI_IS_ROOT_FDO(ParentExtension))
+ {
+ /* And encode the parent's device and function number as well */
+ PdoExtension = ParentExtension->PhysicalDeviceObject->DeviceExtension;
+ PciIdPrintfAppend(&IdBuffer,
+ "%02X",
+ (PdoExtension->Slot.u.bits.DeviceNumber << 3) |
+ PdoExtension->Slot.u.bits.FunctionNumber);
+ }
+ break;
+
+ default:
+
+ /* Unknown query type */
+ DPRINT1("PciQueryId expected ID type = %d\n", QueryType);
+ return STATUS_NOT_SUPPORTED;
+ }
+
+ /* Something should've been generated if this has been reached */
+ ASSERT(IdBuffer.Count > 0);
+
+ /* Allocate the final string buffer to hold the ID */
+ StringBuffer = ExAllocatePoolWithTag(PagedPool, IdBuffer.TotalLength, 'BicP');
+ if (!StringBuffer) return STATUS_INSUFFICIENT_RESOURCES;
+
+ /* Build the UNICODE_STRING structure for it */
+ DPRINT1("PciQueryId(%d)\n", QueryType);
+ DestinationString.Buffer = StringBuffer;
+ DestinationString.MaximumLength = IdBuffer.TotalLength;
+
+ /* Loop every ID in the buffer */
+ for (i = 0; i < IdBuffer.Count; i++)
+ {
+ /* Select the ANSI_STRING for the ID */
+ NextString = &IdBuffer.Strings[i];
+ DPRINT1(" <- \"%s\"\n", NextString->Buffer);
+
+ /* Convert it to a UNICODE_STRING */
+ Status = RtlAnsiStringToUnicodeString(&DestinationString, NextString, FALSE);
+ ASSERT(NT_SUCCESS(Status));
+
+ /* Add it into the final destination buffer */
+ Size = IdBuffer.StringSize[i];
+ DestinationString.MaximumLength -= Size;
+ DestinationString.Buffer += (Size / sizeof(WCHAR));
+ }
+
+ /* Return the buffer to the caller and return status (should be success) */
+ *Buffer = StringBuffer;
+ return Status;
+}
+
+NTSTATUS
+NTAPI
+PciQueryDeviceText(IN PPCI_PDO_EXTENSION PdoExtension,
+ IN DEVICE_TEXT_TYPE QueryType,
+ IN ULONG Locale,
+ OUT PWCHAR *Buffer)
+{
+ PWCHAR MessageBuffer, LocationBuffer;
+ ULONG Length;
+ NTSTATUS Status;
+
+ /* Check what the caller is requesting */
+ switch (QueryType)
+ {
+ case DeviceTextDescription:
+
+ /* Get the message from the resource section */
+ MessageBuffer = PciGetDeviceDescriptionMessage(PdoExtension->BaseClass,
+ PdoExtension->SubClass);
+
+ /* Return it to the caller, and select proper status code */
+ *Buffer = MessageBuffer;
+ Status = MessageBuffer ? STATUS_SUCCESS : STATUS_NOT_SUPPORTED;
+ break;
+
+ case DeviceTextLocationInformation:
+
+ /* Get the message from the resource section */
+ MessageBuffer = PciGetDescriptionMessage(0x10000, &Length);
+ if (!MessageBuffer)
+ {
+ /* It should be there, but fail if it wasn't found for some reason */
+ Status = STATUS_NOT_SUPPORTED;
+ break;
+ }
+
+ /* Add space for a null-terminator, and allocate the buffer */
+ Length += 2 * sizeof(UNICODE_NULL);
+ LocationBuffer = ExAllocatePoolWithTag(PagedPool,
+ Length * sizeof(WCHAR),
+ 'BicP');
+ *Buffer = LocationBuffer;
+
+ /* Check if the allocation succeeded */
+ if (LocationBuffer)
+ {
+ /* Build the location string based on bus, function, and device */
+ swprintf(LocationBuffer,
+ MessageBuffer,
+ PdoExtension->ParentFdoExtension->BaseBus,
+ PdoExtension->Slot.u.bits.FunctionNumber,
+ PdoExtension->Slot.u.bits.DeviceNumber);
+ }
+
+ /* Free the original string from the resource section */
+ ExFreePoolWithTag(MessageBuffer, 0);
+
+ /* Select the correct status */
+ Status = LocationBuffer ? STATUS_SUCCESS : STATUS_INSUFFICIENT_RESOURCES;
+ break;
+
+ default:
+
+ /* Anything else is unsupported */
+ Status = STATUS_NOT_SUPPORTED;
+ break;
+ }
+
+ /* Return whether or not a device text string was indeed found */
+ return Status;
+}
+
/* EOF */
Modified: trunk/reactos/drivers/bus/pcix/pdo.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/bus/pcix/pdo.c?rev…
==============================================================================
--- trunk/reactos/drivers/bus/pcix/pdo.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/bus/pcix/pdo.c [iso-8859-1] Sat Aug 14 17:09:20 2010
@@ -200,9 +200,32 @@
IN PIO_STACK_LOCATION IoStackLocation,
IN PPCI_PDO_EXTENSION DeviceExtension)
{
- UNIMPLEMENTED;
- while (TRUE);
- return STATUS_NOT_SUPPORTED;
+ NTSTATUS Status;
+ PAGED_CODE();
+
+ /* Are ejection relations being queried? */
+ if (IoStackLocation->Parameters.QueryDeviceRelations.Type == EjectionRelations)
+ {
+ /* Call the worker function */
+ Status = PciQueryEjectionRelations(DeviceExtension,
+ (PDEVICE_RELATIONS*)&Irp->
+ IoStatus.Information);
+ }
+ else if (IoStackLocation->Parameters.QueryDeviceRelations.Type == TargetDeviceRelation)
+ {
+ /* The only other relation supported is the target device relation */
+ Status = PciQueryTargetDeviceRelations(DeviceExtension,
+ (PDEVICE_RELATIONS*)&Irp->
+ IoStatus.Information);
+ }
+ else
+ {
+ /* All other relations are unsupported */
+ Status = STATUS_NOT_SUPPORTED;
+ }
+
+ /* Return either the result of the worker function, or unsupported status */
+ return Status;
}
NTSTATUS
@@ -211,9 +234,12 @@
IN PIO_STACK_LOCATION IoStackLocation,
IN PPCI_PDO_EXTENSION DeviceExtension)
{
- UNIMPLEMENTED;
- while (TRUE);
- return STATUS_NOT_SUPPORTED;
+ PAGED_CODE();
+
+ /* Call the worker function */
+ return PciQueryCapabilities(DeviceExtension,
+ IoStackLocation->
+ Parameters.DeviceCapabilities.Capabilities);
}
NTSTATUS
@@ -222,9 +248,11 @@
IN PIO_STACK_LOCATION IoStackLocation,
IN PPCI_PDO_EXTENSION DeviceExtension)
{
- UNIMPLEMENTED;
- while (TRUE);
- return STATUS_NOT_SUPPORTED;
+ PAGED_CODE();
+
+ /* Call the worker function */
+ return PciQueryResources(DeviceExtension,
+ (PCM_RESOURCE_LIST*)&Irp->IoStatus.Information);
}
NTSTATUS
@@ -233,9 +261,12 @@
IN PIO_STACK_LOCATION IoStackLocation,
IN PPCI_PDO_EXTENSION DeviceExtension)
{
- UNIMPLEMENTED;
- while (TRUE);
- return STATUS_NOT_SUPPORTED;
+ PAGED_CODE();
+
+ /* Call the worker function */
+ return PciQueryRequirements(DeviceExtension,
+ (PIO_RESOURCE_REQUIREMENTS_LIST*)&Irp->
+ IoStatus.Information);
}
NTSTATUS
@@ -244,9 +275,15 @@
IN PIO_STACK_LOCATION IoStackLocation,
IN PPCI_PDO_EXTENSION DeviceExtension)
{
- UNIMPLEMENTED;
- while (TRUE);
- return STATUS_NOT_SUPPORTED;
+ PAGED_CODE();
+
+ /* Call the worker function */
+ return PciQueryDeviceText(DeviceExtension,
+ IoStackLocation->
+ Parameters.QueryDeviceText.DeviceTextType,
+ IoStackLocation->
+ Parameters.QueryDeviceText.LocaleId,
+ (PWCHAR*)&Irp->IoStatus.Information);
}
NTSTATUS
@@ -255,9 +292,12 @@
IN PIO_STACK_LOCATION IoStackLocation,
IN PPCI_PDO_EXTENSION DeviceExtension)
{
- UNIMPLEMENTED;
- while (TRUE);
- return STATUS_NOT_SUPPORTED;
+ PAGED_CODE();
+
+ /* Call the worker function */
+ return PciQueryId(DeviceExtension,
+ IoStackLocation->Parameters.QueryId.IdType,
+ (PWCHAR*)&Irp->IoStatus.Information);
}
NTSTATUS
@@ -266,9 +306,12 @@
IN PIO_STACK_LOCATION IoStackLocation,
IN PPCI_PDO_EXTENSION DeviceExtension)
{
- UNIMPLEMENTED;
- while (TRUE);
- return STATUS_NOT_SUPPORTED;
+ PAGED_CODE();
+
+ /* Call the worker function */
+ return PciQueryBusInformation(DeviceExtension,
+ (PPNP_BUS_INFORMATION*)&Irp->
+ IoStatus.Information);
}
NTSTATUS
Modified: trunk/reactos/drivers/bus/pcix/utils.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/bus/pcix/utils.c?r…
==============================================================================
--- trunk/reactos/drivers/bus/pcix/utils.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/bus/pcix/utils.c [iso-8859-1] Sat Aug 14 17:09:20 2010
@@ -1306,4 +1306,455 @@
}
}
+NTSTATUS
+NTAPI
+PciQueryBusInformation(IN PPCI_PDO_EXTENSION PdoExtension,
+ IN PPNP_BUS_INFORMATION* Buffer)
+{
+ PPNP_BUS_INFORMATION BusInfo;
+
+ /* Allocate a structure for the bus information */
+ BusInfo = ExAllocatePoolWithTag(PagedPool,
+ sizeof(PNP_BUS_INFORMATION),
+ 'BicP');
+ if (!BusInfo) return STATUS_INSUFFICIENT_RESOURCES;
+
+ /* Write the correct GUID and bus type identifier, and fill the bus number */
+ BusInfo->BusTypeGuid = GUID_BUS_TYPE_PCI;
+ BusInfo->LegacyBusType = PCIBus;
+ BusInfo->BusNumber = PdoExtension->ParentFdoExtension->BaseBus;
+ return STATUS_SUCCESS;
+}
+
+NTSTATUS
+NTAPI
+PciDetermineSlotNumber(IN PPCI_PDO_EXTENSION PdoExtension,
+ OUT PULONG SlotNumber)
+{
+ PPCI_FDO_EXTENSION ParentExtension;
+ ULONG ResultLength;
+ NTSTATUS Status;
+ PSLOT_INFO SlotInfo;
+
+ /* Check if a $PIR from the BIOS is used (legacy IRQ routing) */
+ ParentExtension = PdoExtension->ParentFdoExtension;
+ DPRINT1("Slot lookup for %d.%d.%d\n",
+ ParentExtension ? ParentExtension->BaseBus : -1,
+ PdoExtension->Slot.u.bits.DeviceNumber,
+ PdoExtension->Slot.u.bits.FunctionNumber);
+ if ((PciIrqRoutingTable) && (ParentExtension))
+ {
+ /* Read every slot information entry */
+ SlotInfo = &PciIrqRoutingTable->Slot[0];
+ DPRINT1("PIR$ %p is %lx bytes, slot 0 is at: %lx\n",
+ PciIrqRoutingTable, PciIrqRoutingTable->TableSize, SlotInfo);
+ while (SlotInfo < (PSLOT_INFO)((ULONG_PTR)PciIrqRoutingTable +
+ PciIrqRoutingTable->TableSize))
+ {
+ DPRINT1("Slot Info: %d.%d->#%d\n",
+ SlotInfo->BusNumber,
+ SlotInfo->DeviceNumber,
+ SlotInfo->SlotNumber);
+
+ /* Check if this slot information matches the PDO being queried */
+ if ((ParentExtension->BaseBus == SlotInfo->BusNumber) &&
+ (PdoExtension->Slot.u.bits.DeviceNumber == SlotInfo->DeviceNumber >> 3) &&
+ (SlotInfo->SlotNumber))
+ {
+ /* We found it, return it and return success */
+ *SlotNumber = SlotInfo->SlotNumber;
+ return STATUS_SUCCESS;
+ }
+
+ /* Try the next slot */
+ SlotInfo++;
+ }
+ }
+
+ /* Otherwise, grab the parent FDO and check if it's the root */
+ if (PCI_IS_ROOT_FDO(ParentExtension))
+ {
+ /* The root FDO doesn't have a slot number */
+ Status = STATUS_UNSUCCESSFUL;
+ }
+ else
+ {
+ /* Otherwise, query the slot/UI address/number as a device property */
+ Status = IoGetDeviceProperty(ParentExtension->PhysicalDeviceObject,
+ DevicePropertyUINumber,
+ sizeof(ULONG),
+ SlotNumber,
+ &ResultLength);
+ }
+
+ /* Return the status of this endeavour */
+ return Status;
+}
+
+NTSTATUS
+NTAPI
+PciGetDeviceCapabilities(IN PDEVICE_OBJECT DeviceObject,
+ IN OUT PDEVICE_CAPABILITIES DeviceCapability)
+{
+ PIRP Irp;
+ NTSTATUS Status;
+ KEVENT Event;
+ PDEVICE_OBJECT AttachedDevice;
+ PIO_STACK_LOCATION IoStackLocation;
+ IO_STATUS_BLOCK IoStatusBlock;
+ PAGED_CODE();
+
+ /* Zero out capabilities and set undefined values to start with */
+ RtlZeroMemory(DeviceCapability, sizeof(DEVICE_CAPABILITIES));
+ DeviceCapability->Size = sizeof(DEVICE_CAPABILITIES);
+ DeviceCapability->Version = 1;
+ DeviceCapability->Address = -1;
+ DeviceCapability->UINumber = -1;
+
+ /* Build the wait event for the IOCTL */
+ KeInitializeEvent(&Event, SynchronizationEvent, FALSE);
+
+ /* Find the device the PDO is attached to */
+ AttachedDevice = IoGetAttachedDeviceReference(DeviceObject);
+
+ /* And build an IRP for it */
+ Irp = IoBuildSynchronousFsdRequest(IRP_MJ_PNP,
+ AttachedDevice,
+ NULL,
+ 0,
+ NULL,
+ &Event,
+ &IoStatusBlock);
+ if (!Irp)
+ {
+ /* The IRP failed, fail the request as well */
+ ObDereferenceObject(AttachedDevice);
+ return STATUS_INSUFFICIENT_RESOURCES;
+ }
+
+ /* Set default status */
+ Irp->IoStatus.Information = 0;
+ Irp->IoStatus.Status = STATUS_NOT_SUPPORTED;
+
+ /* Get a stack location in this IRP */
+ IoStackLocation = IoGetNextIrpStackLocation(Irp);
+ ASSERT(IoStackLocation);
+
+ /* Initialize it as a query capabilities IRP, with no completion routine */
+ RtlZeroMemory(IoStackLocation, sizeof(IO_STACK_LOCATION));
+ IoStackLocation->MajorFunction = IRP_MJ_PNP;
+ IoStackLocation->MinorFunction = IRP_MN_QUERY_CAPABILITIES;
+ IoStackLocation->Parameters.DeviceCapabilities.Capabilities = DeviceCapability;
+ IoSetCompletionRoutine(Irp, NULL, NULL, FALSE, FALSE, FALSE);
+
+ /* Send the IOCTL to the driver */
+ Status = IoCallDriver(AttachedDevice, Irp);
+ if (Status == STATUS_PENDING)
+ {
+ /* Wait for a response and update the actual status */
+ KeWaitForSingleObject(&Event,
+ Executive,
+ KernelMode,
+ FALSE,
+ NULL);
+ Status = Irp->IoStatus.Status;
+ }
+
+ /* Done, dereference the attached device and return the final result */
+ ObDereferenceObject(AttachedDevice);
+ return Status;
+}
+
+NTSTATUS
+NTAPI
+PciQueryPowerCapabilities(IN PPCI_PDO_EXTENSION PdoExtension,
+ IN PDEVICE_CAPABILITIES DeviceCapability)
+{
+ PDEVICE_OBJECT DeviceObject;
+ NTSTATUS Status;
+ DEVICE_CAPABILITIES AttachedCaps;
+ DEVICE_POWER_STATE NewPowerState, DevicePowerState, DeviceWakeLevel, DeviceWakeState;
+ SYSTEM_POWER_STATE SystemWakeState, DeepestWakeState, CurrentState;
+
+ /* Nothing is known at first */
+ DeviceWakeState = PowerDeviceUnspecified;
+ SystemWakeState = DeepestWakeState = PowerSystemUnspecified;
+
+ /* Get the PCI capabilities for the parent PDO */
+ DeviceObject = PdoExtension->ParentFdoExtension->PhysicalDeviceObject;
+ Status = PciGetDeviceCapabilities(DeviceObject, &AttachedCaps);
+ ASSERT(NT_SUCCESS(Status));
+ if (!NT_SUCCESS(Status)) return Status;
+
+ /* Check if there's not an existing device state for S0 */
+ if (!AttachedCaps.DeviceState[PowerSystemWorking])
+ {
+ /* Set D0<->S0 mapping */
+ AttachedCaps.DeviceState[PowerSystemWorking] = PowerDeviceD0;
+ }
+
+ /* Check if there's not an existing device state for S3 */
+ if (!AttachedCaps.DeviceState[PowerSystemShutdown])
+ {
+ /* Set D3<->S3 mapping */
+ AttachedCaps.DeviceState[PowerSystemShutdown] = PowerDeviceD3;
+ }
+
+ /* Check for a PDO with broken, or no, power capabilities */
+ if (PdoExtension->HackFlags & PCI_HACK_NO_PM_CAPS)
+ {
+ /* Unknown wake device states */
+ DeviceCapability->DeviceWake = PowerDeviceUnspecified;
+ DeviceCapability->SystemWake = PowerSystemUnspecified;
+
+ /* No device state support */
+ DeviceCapability->DeviceD1 = FALSE;
+ DeviceCapability->DeviceD2 = FALSE;
+
+ /* No waking from any low-power device state is supported */
+ DeviceCapability->WakeFromD0 = FALSE;
+ DeviceCapability->WakeFromD1 = FALSE;
+ DeviceCapability->WakeFromD2 = FALSE;
+ DeviceCapability->WakeFromD3 = FALSE;
+
+ /* For the rest, copy whatever the parent PDO had */
+ RtlCopyMemory(DeviceCapability->DeviceState,
+ AttachedCaps.DeviceState,
+ sizeof(DeviceCapability->DeviceState));
+ return STATUS_SUCCESS;
+ }
+
+ /* The PCI Device has power capabilities, so read which ones are supported */
+ DeviceCapability->DeviceD1 = PdoExtension->PowerCapabilities.Support.D1;
+ DeviceCapability->DeviceD2 = PdoExtension->PowerCapabilities.Support.D2;
+ DeviceCapability->WakeFromD0 = PdoExtension->PowerCapabilities.Support.PMED0;
+ DeviceCapability->WakeFromD1 = PdoExtension->PowerCapabilities.Support.PMED1;
+ DeviceCapability->WakeFromD2 = PdoExtension->PowerCapabilities.Support.PMED2;
+
+ /* Can the attached device wake from D3? */
+ if (AttachedCaps.DeviceWake != PowerDeviceD3)
+ {
+ /* It can't, so check if this PDO supports hot D3 wake */
+ DeviceCapability->WakeFromD3 = PdoExtension->PowerCapabilities.Support.PMED3Hot;
+ }
+ else
+ {
+ /* It can, is this the root bus? */
+ if (PCI_IS_ROOT_FDO(PdoExtension->ParentFdoExtension))
+ {
+ /* This is the root bus, so just check if it supports hot D3 wake */
+ DeviceCapability->WakeFromD3 = PdoExtension->PowerCapabilities.Support.PMED3Hot;
+ }
+ else
+ {
+ /* Take the minimums? -- need to check with briang at work */
+ UNIMPLEMENTED;
+ }
+ }
+
+ /* Now loop each system power state to determine its device state mapping */
+ for (CurrentState = PowerSystemWorking;
+ CurrentState < PowerSystemMaximum;
+ CurrentState++)
+ {
+ /* Read the current mapping from the attached device */
+ DevicePowerState = AttachedCaps.DeviceState[CurrentState];
+ NewPowerState = DevicePowerState;
+
+ /* The attachee suports D1, but this PDO does not */
+ if ((NewPowerState == PowerDeviceD1) &&
+ !(PdoExtension->PowerCapabilities.Support.D1))
+ {
+ /* Fall back to D2 */
+ NewPowerState = PowerDeviceD2;
+ }
+
+ /* The attachee supports D2, but this PDO does not */
+ if ((NewPowerState == PowerDeviceD2) &&
+ !(PdoExtension->PowerCapabilities.Support.D2))
+ {
+ /* Fall back to D3 */
+ NewPowerState = PowerDeviceD3;
+ }
+
+ /* Set the mapping based on the best state supported */
+ DeviceCapability->DeviceState[CurrentState] = NewPowerState;
+
+ /* Check if sleep states are being processed, and a mapping was found */
+ if ((CurrentState < PowerSystemHibernate) &&
+ (NewPowerState != PowerDeviceUnspecified))
+ {
+ /* Save this state as being the deepest one found until now */
+ DeepestWakeState = CurrentState;
+ }
+
+ /*
+ * Finally, check if the computed sleep state is within the states that
+ * this device can wake the system from, and if it's higher or equal to
+ * the sleep state mapping that came from the attachee, assuming that it
+ * had a valid mapping to begin with.
+ *
+ * It this is the case, then make sure that the computed sleep state is
+ * matched by the device's ability to actually wake from that state.
+ *
+ * For devices that support D3, the PCI device only needs Hot D3 as long
+ * as the attachee's state is less than D3. Otherwise, if the attachee
+ * might also be at D3, this would require a Cold D3 wake, so check that
+ * the device actually support this.
+ */
+ if ((CurrentState < AttachedCaps.SystemWake) &&
+ (NewPowerState >= DevicePowerState) &&
+ (DevicePowerState != PowerDeviceUnspecified) &&
+ (((NewPowerState == PowerDeviceD0) && (DeviceCapability->WakeFromD0)) ||
+ ((NewPowerState == PowerDeviceD1) && (DeviceCapability->WakeFromD1)) ||
+ ((NewPowerState == PowerDeviceD2) && (DeviceCapability->WakeFromD2)) ||
+ ((NewPowerState == PowerDeviceD3) &&
+ (PdoExtension->PowerCapabilities.Support.PMED3Hot) &&
+ ((DevicePowerState < PowerDeviceD3) ||
+ (PdoExtension->PowerCapabilities.Support.PMED3Cold)))))
+ {
+ /* The mapping is valid, so this will be the lowest wake state */
+ SystemWakeState = CurrentState;
+ DeviceWakeState = NewPowerState;
+ }
+ }
+
+ /* Read the current wake level */
+ DeviceWakeLevel = PdoExtension->PowerState.DeviceWakeLevel;
+
+ /* Check if the attachee's wake levels are valid, and the PDO's is higher */
+ if ((AttachedCaps.SystemWake != PowerSystemUnspecified) &&
+ (AttachedCaps.DeviceWake != PowerDeviceUnspecified) &&
+ (DeviceWakeLevel != PowerDeviceUnspecified) &&
+ (DeviceWakeLevel >= AttachedCaps.DeviceWake))
+ {
+ /* Inherit the system wake from the attachee, and this PDO's wake level */
+ DeviceCapability->SystemWake = AttachedCaps.SystemWake;
+ DeviceCapability->DeviceWake = DeviceWakeLevel;
+
+ /* Now check if the wake level is D0, but the PDO doesn't support it */
+ if ((DeviceCapability->DeviceWake == PowerDeviceD0) &&
+ !(DeviceCapability->WakeFromD0))
+ {
+ /* Bump to D1 */
+ DeviceCapability->DeviceWake = PowerDeviceD1;
+ }
+
+ /* Now check if the wake level is D1, but the PDO doesn't support it */
+ if ((DeviceCapability->DeviceWake == PowerDeviceD1) &&
+ !(DeviceCapability->WakeFromD1))
+ {
+ /* Bump to D2 */
+ DeviceCapability->DeviceWake = PowerDeviceD2;
+ }
+
+ /* Now check if the wake level is D2, but the PDO doesn't support it */
+ if ((DeviceCapability->DeviceWake == PowerDeviceD2) &&
+ !(DeviceCapability->WakeFromD2))
+ {
+ /* Bump it to D3 */
+ DeviceCapability->DeviceWake = PowerDeviceD3;
+ }
+
+ /* Now check if the wake level is D3, but the PDO doesn't support it */
+ if ((DeviceCapability->DeviceWake == PowerDeviceD3) &&
+ !(DeviceCapability->WakeFromD3))
+ {
+ /* Then no valid wake state exists */
+ DeviceCapability->DeviceWake = PowerDeviceUnspecified;
+ DeviceCapability->SystemWake = PowerSystemUnspecified;
+ }
+
+ /* Check if no valid wake state was found */
+ if ((DeviceCapability->DeviceWake == PowerDeviceUnspecified) ||
+ (DeviceCapability->SystemWake == PowerSystemUnspecified))
+ {
+ /* Check if one was computed earlier */
+ if ((SystemWakeState != PowerSystemUnspecified) &&
+ (DeviceWakeState != PowerDeviceUnspecified))
+ {
+ /* Use the wake state that had been computed earlier */
+ DeviceCapability->DeviceWake = DeviceWakeState;
+ DeviceCapability->SystemWake = SystemWakeState;
+
+ /* If that state was D3, then the device supports Hot/Cold D3 */
+ if (DeviceWakeState == PowerDeviceD3) DeviceCapability->WakeFromD3 = TRUE;
+ }
+ }
+
+ /*
+ * Finally, check for off states (lower than S3, such as hibernate) and
+ * make sure that the device both supports waking from D3 as well as
+ * supports a Cold wake
+ */
+ if ((DeviceCapability->SystemWake > PowerSystemSleeping3) &&
+ ((DeviceCapability->DeviceWake != PowerDeviceD3) ||
+ !(PdoExtension->PowerCapabilities.Support.PMED3Cold)))
+ {
+ /* It doesn't, so pick the computed lowest wake state from earlier */
+ DeviceCapability->SystemWake = DeepestWakeState;
+ }
+
+ /* Set the PCI Specification mandated maximum latencies for transitions */
+ DeviceCapability->D1Latency = 0;
+ DeviceCapability->D2Latency = 2;
+ DeviceCapability->D3Latency = 100;
+
+ /* Sanity check */
+ ASSERT(DeviceCapability->DeviceState[PowerSystemWorking] == PowerDeviceD0);
+ }
+ else
+ {
+ /* No valid sleep states, no latencies to worry about */
+ DeviceCapability->D1Latency = 0;
+ DeviceCapability->D2Latency = 0;
+ DeviceCapability->D3Latency = 0;
+ }
+
+ /* This function always succeeds, even without power management support */
+ return STATUS_SUCCESS;
+}
+
+NTSTATUS
+NTAPI
+PciQueryCapabilities(IN PPCI_PDO_EXTENSION PdoExtension,
+ IN OUT PDEVICE_CAPABILITIES DeviceCapability)
+{
+ NTSTATUS Status;
+
+ /* A PDO ID is never unique, and its address is its function and device */
+ DeviceCapability->UniqueID = FALSE;
+ DeviceCapability->Address = PdoExtension->Slot.u.bits.FunctionNumber |
+ (PdoExtension->Slot.u.bits.DeviceNumber << 16);
+
+ /* Check for host bridges */
+ if ((PdoExtension->BaseClass == PCI_CLASS_BRIDGE_DEV) &&
+ (PdoExtension->SubClass == PCI_SUBCLASS_BR_HOST))
+ {
+ /* Raw device opens to a host bridge are acceptable */
+ DeviceCapability->RawDeviceOK = TRUE;
+ }
+ else
+ {
+ /* Otherwise, other PDOs cannot be directly opened */
+ DeviceCapability->RawDeviceOK = FALSE;
+ }
+
+ /* PCI PDOs are pretty fixed things */
+ DeviceCapability->LockSupported = FALSE;
+ DeviceCapability->EjectSupported = FALSE;
+ DeviceCapability->Removable = FALSE;
+ DeviceCapability->DockDevice = FALSE;
+
+ /* The slot number is stored as a device property, go query it */
+ PciDetermineSlotNumber(PdoExtension, &DeviceCapability->UINumber);
+
+ /* Finally, query and power capabilities and convert them for PnP usage */
+ Status = PciQueryPowerCapabilities(PdoExtension, DeviceCapability);
+
+ /* Dump the capabilities if it all worked, and return the status */
+ if (NT_SUCCESS(Status)) PciDebugDumpQueryCapabilities(DeviceCapability);
+ return Status;
+}
+
/* EOF */
Author: cgutman
Date: Sat Aug 14 14:55:12 2010
New Revision: 48546
URL: http://svn.reactos.org/svn/reactos?rev=48546&view=rev
Log:
[NTOSKRNL]
- Move to the next entry in the thread IRP list before calling IoCancelIrp because if everything works as expected and IoCompleteRequest is called, we could end up with the IRP ripped out from under us before can move to the next element
- See issue #5550 for details.
Modified:
trunk/reactos/ntoskrnl/io/iomgr/irp.c
Modified: trunk/reactos/ntoskrnl/io/iomgr/irp.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/io/iomgr/irp.c?re…
==============================================================================
--- trunk/reactos/ntoskrnl/io/iomgr/irp.c [iso-8859-1] (original)
+++ trunk/reactos/ntoskrnl/io/iomgr/irp.c [iso-8859-1] Sat Aug 14 14:55:12 2010
@@ -1047,14 +1047,12 @@
NextEntry = ListHead->Flink;
while (ListHead != NextEntry)
{
- /* Get the IRP */
+ /* Get the IRP and move to the next entry */
Irp = CONTAINING_RECORD(NextEntry, IRP, ThreadListEntry);
+ NextEntry = NextEntry->Flink;
/* Cancel it */
IoCancelIrp(Irp);
-
- /* Move to the next entry */
- NextEntry = NextEntry->Flink;
}
/* Wait 100 milliseconds */
Author: cgutman
Date: Sat Aug 14 13:48:31 2010
New Revision: 48545
URL: http://svn.reactos.org/svn/reactos?rev=48545&view=rev
Log:
[WS2_32]
- Create a temporary variable and pass that to WSAIoctl for the bytes returned value instead of passing argp and corrupting the value we just retrieved
Modified:
trunk/reactos/dll/win32/ws2_32/misc/dllmain.c
Modified: trunk/reactos/dll/win32/ws2_32/misc/dllmain.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/dll/win32/ws2_32/misc/dllm…
==============================================================================
--- trunk/reactos/dll/win32/ws2_32/misc/dllmain.c [iso-8859-1] (original)
+++ trunk/reactos/dll/win32/ws2_32/misc/dllmain.c [iso-8859-1] Sat Aug 14 13:48:31 2010
@@ -586,13 +586,15 @@
IN LONG cmd,
IN OUT ULONG FAR* argp)
{
+ ULONG tmp;
+
return WSAIoctl(s,
cmd,
argp,
sizeof(ULONG),
argp,
sizeof(ULONG),
- argp,
+ &tmp,
0,
0);
}