📄 pciscan.c
字号:
//
// Iterate over all functions
//
for ( FunctionNumber =
firstFunction?0:returnSlotData->u.bits.FunctionNumber;
FunctionNumber < PCI_MAX_FUNCTION ;
FunctionNumber++)
{ /* functions loop */
slotData.u.bits.FunctionNumber = FunctionNumber;
KdPrint( ("pciScan: FindPCI - call HalGetBusData DeviceNumber= %x, Function = %x, busNumber = %x ",
slotData.u.bits.DeviceNumber,
slotData.u.bits.FunctionNumber,
busNumber) );
RtlZeroMemory(&pciData, sizeof(PCI_COMMON_CONFIG));
bytesReturned = HalGetBusData( PCIConfiguration,
busNumber,
slotData.u.AsULONG,
&pciData,
sizeof(PCI_COMMON_CONFIG));
if (2 == bytesReturned) // device/function does not exist
{ /* no device/function */
KdPrint( (" - no match 2 returned pciData.VendorID = %x %x\n",
pciData.VendorID,
slotData.u.AsULONG) );
//
// MUST CONTINUE WITH LOOP --
// functions do not have to be consective
//
} /* no device/function */
else
if (0 == bytesReturned) // bus does not exist
{ /* no bus */
KdPrint( (" - no match 0 returned pciData.VendorID = %x %x\n",
pciData.VendorID,
slotData.u.AsULONG) );
//
// We can skip to next bus
// set flag to break out of device loop
// and break out of function loop
//
nextBus = TRUE;
break;
} /* no bus */
else
if (0xffff == pciData.VendorID)
{ /* invalid vendor ID */
KdPrint( (" - no match PCI_INVALID_VENDER_ID HalGetBusData pciData.VendorID = %x\n",
pciData.VendorID) );
} /* invalid vendor ID */
else
if ( ((0xFFFF == pciVendorId)
|| ( pciData.VendorID == pciVendorId )) &&
((0xFFFF == pciDeviceId)
|| ( pciData.DeviceID == pciDeviceId)))
{ /* found next */
// Found it this is the next instance of
// this card type
KdPrint( ("\npciScan: ( busNumber, device, function ) = ( %x, %x, %x )\n",
busNumber,
slotData.u.bits.DeviceNumber,
slotData.u.bits.FunctionNumber));
dumpPciConfig( pciData );
KdPrint( ("\n\n") );
*returnSlotData = slotData;
*returnPciData = pciData;
*returnBusNumber = busNumber;
KdPrint( ("pciScan: exiting\n") );
return TRUE;
} /* found next */
else
{ /* does not match */
KdPrint( (" - no match pciData.VendorID = %x %x\n", pciData.VendorID, slotData.u.AsULONG) );
} /* does not match */
} /* functions loop */
if (nextBus)
break; // break to next bus
} /* devices loop */
} /* busses loop */
KdPrint( ("pciScan: exiting\n") );
return FALSE;
} // end pciScanFindPCI()
/****************************************************************************
Function:
pciScanDeviceControl
Arguments:
Description:
Returns:
*****************************************************************************/
NTSTATUS pciScanDeviceControl(
IN PDEVICE_OBJECT DeviceObject,
IN PIRP Irp )
{
NTSTATUS ret = STATUS_SUCCESS;
PIO_STACK_LOCATION irpStack;
PCISCAN_OUTPUT *pOutBuffer;
PCISCAN_DEVICE_EXTENSION *extension;
PCI_SLOT_NUMBER returnSlotData;
PCI_COMMON_CONFIG returnPciData;
unsigned int returnBusNumber;
KdPrint( ("pciScan: Device Control!!\n") );
extension = (PCISCAN_DEVICE_EXTENSION *) DeviceObject->DeviceExtension;
irpStack = IoGetCurrentIrpStackLocation(Irp);
pOutBuffer = (PCISCAN_OUTPUT *)Irp->UserBuffer; // for buffered i/o
switch(irpStack->Parameters.DeviceIoControl.IoControlCode)
{ /* IOCTL */
case IOCTL_PCISCAN_GET_FIRST:
KdPrint( ("pciScan: Device Control -- enter GET FIRST\n") );
if (pciScanIteratePCI( TRUE, 0xffff, 0xffff,
&extension->returnSlotData,
&extension->returnPciData,
&extension->returnBusNumber ))
{ /* got first */
KdPrint( ("pciScanIoctl: found first pci device\n") );
pOutBuffer->SlotData = extension->returnSlotData;
pOutBuffer->PciData = extension->returnPciData;
pOutBuffer->BusNumber = extension->returnBusNumber;
ret = STATUS_SUCCESS;
break;
} /* got first */
else
{ /* failed first */
KdPrint( ("pciScanIoctl: FAILED find first pci device\n") );
ret = STATUS_UNSUCCESSFUL;
break;
} /* failed first */
break;
case IOCTL_PCISCAN_GET_NEXT:
KdPrint( ("pciScan: Device Control -- enter GET NEXT\n") );
if (pciScanIteratePCI( FALSE, 0xffff, 0xffff,
&extension->returnSlotData,
&extension->returnPciData,
&extension->returnBusNumber ))
{ /* got next */
KdPrint( ("\npciScanIoctl: found next pci device\n") );
pOutBuffer->SlotData = extension->returnSlotData;
pOutBuffer->PciData = extension->returnPciData;
pOutBuffer->BusNumber = extension->returnBusNumber;
ret = STATUS_SUCCESS;
break;
} /* got next */
else
{ /* no more */
KdPrint( ("pciScanIoctl: FAILED find next pci device\n") );
ret = STATUS_UNSUCCESSFUL;
break;
} /* no more */
break;
default:
ret = STATUS_UNSUCCESSFUL;
} /* IOCTL */
KdPrint( ("pciScan: Device Control -- return\n") );
//
// Fill these in before calling IoCompleteRequest.
//
Irp->IoStatus.Status = ret;
Irp->IoStatus.Information = 0;
IoCompleteRequest( Irp, IO_NO_INCREMENT );
return ret;
}
VOID pciScanUnload( IN PDRIVER_OBJECT DriverObject)
{
UNICODE_STRING uniDosNameString;
//
// All *THIS* driver needs to do is to delete the allocated memory objects,
// the device object and the
// symbolic link between our device name and the Win32 visible name.
//
// Almost every other driver ever witten would need to do a
// significant amount of work here deallocating stuff.
//
KdPrint( ("pciScan: Unloading!!\n") );
//
// Create counted string version of our Win32 device name.
//
RtlInitUnicodeString( &uniDosNameString, DOS_DEVICE_NAME );
//
// Delete the link from our device name to a name in the Win32 namespace.
//
IoDeleteSymbolicLink( &uniDosNameString );
//
// Finally delete our device object
//
IoDeleteDevice( DriverObject->DeviceObject );
}
NTSTATUS pciScanOpen(
IN PDEVICE_OBJECT DeviceObject,
IN PIRP Irp )
{
KdPrint( ("pciScan: Opened!!\n") );
//
// No need to do anything.
//
//
// Fill these in before calling IoCompleteRequest.
//
// DON'T get cute and try to use the status field of
// the irp in the return status. That IRP IS GONE as
// soon as you call IoCompleteRequest.
//
Irp->IoStatus.Status = STATUS_SUCCESS;
Irp->IoStatus.Information = 0;
IoCompleteRequest( Irp, IO_NO_INCREMENT );
return STATUS_SUCCESS;
}
NTSTATUS pciScanClose(
IN PDEVICE_OBJECT DeviceObject,
IN PIRP Irp )
{
KdPrint( ("pciScan: Closed!!\n") );
//
// No need to do anything.
//
//
// Fill these in before calling IoCompleteRequest.
//
// DON'T get cute and try to use the status field of
// the irp in the return status. That IRP IS GONE as
// soon as you call IoCompleteRequest.
//
Irp->IoStatus.Status = STATUS_SUCCESS;
Irp->IoStatus.Information = 0;
IoCompleteRequest( Irp, IO_NO_INCREMENT );
return STATUS_SUCCESS;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -