中断处理
来源:互联网 发布:json数据转化成数组 编辑:程序博客网 时间:2024/06/06 06:31
版权声明:本文采用【DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE】协议
由于PCI设备的多样化,而系统的中断数量是有限的。所以采用多个设备共用一个中断号。在获取到中断后,操作系统会询问这条中断线上的所以设备。设备通过查询中断寄存器就可以知道是不是自己的中断,如果不是则在中断处理例程中返回FALSE,如果是则处理并返回TRUE。
在操作系统收到IRP_MN_START_DEVICE请求时,PDO会获取到中断相关的资源。参考例子如下:
NTSTATUS GetPciResource(IN PDEVICE_EXTENSION pExtension, IN PCM_PARTIAL_RESOURCE_LIST list){ PDEVICE_OBJECT fdo = pExtension->fdo; KINTERRUPT_MODE mode; BOOLEAN irqshare; BOOLEAN gotinterrupt = FALSE; PCM_PARTIAL_RESOURCE_DESCRIPTOR resource = &list->PartialDescriptors[0]; ULONG nres = list->Count; for (ULONG i = 0; i < nres; ++i, ++resource) { // for each resource switch (resource->Type) { // switch on resource type case CmResourceTypeInterrupt: { KdPrint(("resource->Type = CmResourceTypeInterrupt\n")); pExtension->Irql = (KIRQL)resource->u.Interrupt.Level; pExtension->Vector = resource->u.Interrupt.Vector; pExtension->Affinity = resource->u.Interrupt.Affinity; mode = (resource->Flags == CM_RESOURCE_INTERRUPT_LATCHED) ? Latched : LevelSensitive; irqshare = (resource->ShareDisposition == CmResourceShareShared); gotinterrupt = TRUE; }break; default: KdPrint(("Unexpected I/O resource type %d\n", resource->Type)); break; } // switch on resource type } // for each resource return STATUS_SUCCESS;}
- 3
获取到中断资源后,驱动程序可以使用IoConnectInterrupt将中断与中断处理函数挂接。IoConnectInterrupt的原型如下:
NTSTATUS IoConnectInterrupt( _Out_ PKINTERRUPT *InterruptObject, //输出一个INTERRUPT结构的中断对象 _In_ PKSERVICE_ROUTINE ServiceRoutine, //中断处理例程 _In_opt_ PVOID ServiceContext, //中断处理例程的参数 _In_opt_ PKSPIN_LOCK SpinLock, //用于同步的自旋锁 _In_ ULONG Vector, //中断向量号,在PDO获得 _In_ KIRQL Irql, //中断优先级,在PDO获得 _In_ KIRQL SynchronizeIrql, //同IRQL _In_ KINTERRUPT_MODE InterruptMode, //中断模式,Latched(电平触发),LevelSensitive (边沿触发) _In_ BOOLEAN ShareVector, //是否与其他设备共享中断向量,设为TRUE _In_ KAFFINITY ProcessorEnableMask,//CPU屏蔽位,在PDO获得 _In_ BOOLEAN FloatingSave //X86平台默认为FALSE);
- 1
NTSTATUS status = IoConnectInterrupt(&pExtension->pInterruptObject, (PKSERVICE_ROUTINE)OnInterrupt, (PVOID)pExtension, NULL, pExtension->Vector, pExtension->Irql, pExtension->Irql, LevelSensitive, TRUE, pExtension->Affinity, FALSE); if (!NT_SUCCESS(status)) { KdPrint(("IoConnectInterrupt failed - %X\n", status)); return status; }
中断处理例程原型如下:
KSERVICE_ROUTINE InterruptService;BOOLEAN InterruptService( _In_ struct _KINTERRUPT *Interrupt, _In_ PVOID ServiceContext){ ... }
值得注意的是,如果不是自己设备产生的中断,一定要返回FALSE,如果是自己设备的中断,则必须清除掉中断。
阅读全文
0 0
- 中断和中断处理
- 中断处理--串口中断
- 中断及中断处理
- 中断和中断处理
- 中断和中断处理
- 中断处理
- 中断处理
- 中断处理
- 中断处理
- 中断处理
- 中断处理
- 中断处理
- 中断处理
- 中断处理
- 中断处理
- 中断处理
- 中断处理
- 中断处理
- 压力测试之badboy和Jmeter的简单使用方法
- 如何理解Python的With语句?
- 两层fragment内层切换不显示的问题
- 终端控制文件隐藏和显示
- RadioGroup 和RadioButton制作Tab修改RadioButton的大小
- 中断处理
- 详解设计模式——模板方法模式
- 小白次幂的Git使用教程
- 0级,1级,2级监听
- 详解设计模式——适配器模式
- 死锁
- iOS--脚本配置Xcode Project(打包)
- Resource is out of sync with the file system的解决办法
- Linux子进程创建