|
发表于 2005-5-23 14:21:43
|
显示全部楼层
wdm驱动程序如何能够访问pci设备的配置空间
NTSTATUS PciConfigRegisterRead(PDEVICE_OBJECT fdo,ULONG *pReadValue,USHORT offset,UCHAR Length)
{
PIRP pIrp;
KEVENT event;
NTSTATUS status;
PIO_STACK_LOCATION stack;
UCHAR ReadLen;
pIrp = IoAllocateIrp(fdo->StackSize,FALSE
if (pIrp == NULL)
{
return STATUS_INSUFFICIENT_RESOURCES;
}
// Initialize kernel event
KeInitializeEvent(&event,NotificationEvent,FALSE);
stack =IoGetNextIrpStackLocation(pIrp);
switch ( Length )
{
case 1:ReadLen = sizeof(UCHAR);break;
case 2:ReadLen = sizeof(USHORT);break;
case 4:ReadLen = sizeof(ULONG);break;
default:ReadLen = sizeof(ULONG);break;
}
// Fill the IRP
pIrp->IoStatus.Status = STATUS_NOT_SUPPORTED;
stack->MajorFunction = IRP_MJ_PNP;
stack->MinorFunction = IRP_MN_READ_CONFIG;
stack->arameters.ReadWriteConfig.WhichSpace = 0;
stack->arameters.ReadWriteConfig.Buffer = pReadValue;
stack->arameters.ReadWriteConfig.Offset = offset;
stack->Parameters.ReadWriteConfig.Length = ReadLen;
IoSetCompletionRoutine(pIrp,(PIO_COMPLETION_ROUTINE)OnRequestComplete,(PVOID)&event,TRUE,TRUE,TRUE);
// Send the packet
status =IoCallDriver(fdo,pIrp);
if (status == STATUS_PENDING)
{
// Wait for completion
KeWaitForSingleObject(&event,Executive,KernelMode,FALSE,NULL);
status = pIrp->IoStatus.Status;
}
// Release the IRP
IoFreeIrp(pIrp);
return status;
}
NTSTATUS OnRequestComplete(PDEVICE_OBJECT fdo,PIRP pIrp,PKEVENT pKEvent)
{
KeSetEvent(pKEvent,0,FALSE);
return STATUS_MORE_PROCESSING_REQUIRED;
} |
|