나는 지난 주 비슷한 비슷한 고투를 해왔다. MSI-X 인터럽트보다는 작동하지 않는 일반 MSI 인터럽트를 얻으려고하기 때문에 응용 프로그램이 약간 다릅니다. 하지만 WDF 프레임 워크는 거의 같은 방식으로 사용하고 있습니다.
나는 원래 질문을 2013 년 4 월경에 게시했지만 업데이트가 없다는 것을 알고 있습니다. 원래 문제를 해결 했습니까? 그렇다면 자신의 솔루션을보고 싶습니다.
내 WDF 드라이버에서 들어오는 하드웨어 리소스 목록을 매핑하고 WdfCmResourceListGetDescriptor() 함수를 사용하여 구문 분석하여 WDFCMRESLIST 목록의 각 PCM_PARTIAL_RESOURCE_DESCRIPTOR 항목을 검사합니다. 하나의 CmResourceTypeInterrupt 디스크립터를 얻을 수 있었지만 MSI 인터럽트 대신 레거시 인터럽트가 항상있었습니다. 내 장치가 MSI를 지원합니다. 내가 설명한대로 내 .inf 파일에 추가 레지스트리 항목을 설정 한 후에도 MSI 설명자가 리소스 목록에없는 이유를 알지 못했습니다.
내 .inf 파일에 오타가있는 것으로 나타났습니다. 내 장치 설치 섹션에 ".HW"접미사를 추가하는 것을 잊었습니다. 이 접미어를 추가하면 버스 관리자가 장치의 pcie 구성 주소를 수정하고 해당 MSI 인터럽트 리소스 설명자를 만들 수 있습니다.이 리소스 설명자는 드라이버가 연결해야합니다. MSI는 인터럽트 자원 기술자 (a evtMapHWResources 콜백에서 예) 자원 목록에서 발견
[Standard.NT$ARCH$]
%tdvr.DeviceDesc%=tdvr_Device, PCI\VEN_104C&DEV_B800
[tdvr_Device.NT]
CopyFiles=Drivers_Dir
[tdvr_Device.NT.HW]
AddReg=MSI_Interrupts
[Drivers_Dir]
tdvr.sys
;http://msdn.microsoft.com/en-us/library/windows/hardware/ff544246(v=vs.85).aspx
;To receive message-signaled interrupts (MSIs), a driver's INF file must enable MSIs in the
;registry during installation. Use the Interrupt Management\MessageSignaledInterruptProperties
;subkey of the device's hardware key to enable MSI support.
[MSI_Interrupts]
HKR,Interrupt Management,,0x00000010
HKR,Interrupt Management\MessageSignaledInterruptProperties,,0x00000010
HKR,Interrupt Management\MessageSignaledInterruptProperties,MSISupported,0x00010001,1
는 기술자가 WdfInterruptCreate() 함수에 대한 입력으로서 사용된다. 여기에 "tdvr"접두사는 내 자신의 드라이버 명명 규칙을위한 것입니다.
NTSTATUS
tdvrConfigureInterrupts(
_Inout_ PDEVICE_CONTEXT deviceContext,
_In_ PCM_PARTIAL_RESOURCE_DESCRIPTOR interruptDescRaw,
_In_ PCM_PARTIAL_RESOURCE_DESCRIPTOR interruptDescTranslated
)
{
NTSTATUS status;
PAGED_CODE();
FuncEntry();
// What kind of interrupt has been provided?
if (CM_RESOURCE_INTERRUPT_MESSAGE & interruptDescTranslated->Flags)
{
TraceInterrupt(TRACE_LEVEL_INFORMATION,
"Message Interrupt level 0x%0x, Vector 0x%0x, MessageCount %u\n"
,interruptDescTranslated->u.MessageInterrupt.Translated.Level
,interruptDescTranslated->u.MessageInterrupt.Translated.Vector
,interruptDescTranslated->u.MessageInterrupt.Raw.MessageCount
);
}
else
{
TraceInterrupt(TRACE_LEVEL_INFORMATION,
"Legacy Interrupt level: 0x%0x, Vector: 0x%0x\n"
,interruptDescTranslated->u.Interrupt.Level
,interruptDescTranslated->u.Interrupt.Vector
);
}
//
// Create WDFINTERRUPT object.
//
WDF_INTERRUPT_CONFIG interruptConfig;
WDF_INTERRUPT_CONFIG_INIT(
&interruptConfig,
tdvrEvtInterruptIsr,
tdvrEvtInterruptDpc
);
// Each interrupt has some context data
WDF_OBJECT_ATTRIBUTES interruptAttributes;
WDF_OBJECT_ATTRIBUTES_INIT_CONTEXT_TYPE(
&interruptAttributes,
INTERRUPT_CONTEXT
);
//
// These first two callbacks will be called at DIRQL. Their job is to
// enable and disable interrupts.
//
interruptConfig.EvtInterruptEnable = tdvrEvtInterruptEnable;
interruptConfig.EvtInterruptDisable = tdvrEvtInterruptDisable;
// If the driver calls WdfInterruptCreate from EvtDriverDeviceAdd, the InterruptRaw and
// InterruptTranslated members of the WDF_INTERRUPT_CONFIG structure must be NULL.
// the driver calls WdfInterruptCreate from EvtDevicePrepareHardware, these members must both be valid.
interruptConfig.InterruptTranslated = interruptDescTranslated;
interruptConfig.InterruptRaw = interruptDescRaw;
// Our driver must call WdfInterruptCreate once for each interrupt vector that its device requires.
// If the device supports message-signaled interrupts (MSI), the driver must create an interrupt object
// for each message that the device can support.
status = WdfInterruptCreate(
deviceContext->WdfDevice,
&interruptConfig,
&interruptAttributes,
&deviceContext->WdfInterrupt
);
if (!NT_SUCCESS(status))
{
TraceInterrupt(TRACE_LEVEL_ERROR, "WdfInterruptCreate FAILED: %!STATUS!\n", status);
}
else
{
PINTERRUPT_CONTEXT interruptContext = InterruptGetContext(deviceContext->WdfInterrupt);
// do whatever with context info
}
FuncExit();
return status;
}
나는 지금 바라건대이 모든 것을 알아 냈습니다.하지만 어쨌든 기여하기 위해 뭔가를 게시 할 것이라고 생각했습니다.
감사합니다. 불행히도, 나는별로 추가하지 않습니다. 우리에게이 프로젝트에 다시 할당되었을 때, 우리는 디버그 테스터가 잘못된 드라이버를 배포하고 있다는 사실을 깨닫고 실제로 메시지가 신호를 받았다. 나는 우리가 알아 차 렸지만 당신이하지 않는 것을 알아 차린다.'HKR, Interrupt Management \ MessageSignaledInterruptProperties, MessageNumberLimit, 0x00010001,8'. 차이가 있는지 확실하지 않습니다. 미안하지만 나는 더 많은 도움을 줄 수는 없지만 행운을 빈다. – 8bitcartridge