ACPI!IsNsobjPciBus看event从主线程到异步线程--非常重要
1: kd> g
Breakpoint 15 hit
eax=8996cd78 ebx=899c5690 ecx=8996dc38 edx=00000000 esi=8996e010 edi=00000000
eip=f7448630 esp=f78f2d10 ebp=f78f2d48 iopl=0 nv up ei pl zr na pe nc
cs=0008 ss=0010 ds=0023 es=0023 fs=0030 gs=0000 efl=00000246
ACPI!IsNsobjPciBus:
f7448630 55 push ebp
1: kd> kc
00 ACPI!IsNsobjPciBus
01 ACPI!EnableDisableRegions
02 ACPI!ACPIFilterIrpStartDeviceWorker
03 nt!ExpWorkerThread
04 nt!PspSystemThreadStartup
05 nt!KiThreadStartup
status = IsPciBusAsync( Device,
AmlisuppCompletePassive,
(PVOID)&getDataContext, 第二个参数:
&result );
1: kd> dv
Device = 0x8996e010
result = 0x00 ''
getDataContext = struct AMLISUPP_CONTEXT_PASSIVE
1: kd> kc
00 ACPI!IsPciBusAsync
01 ACPI!IsNsobjPciBus
02 ACPI!EnableDisableRegions
03 ACPI!ACPIFilterIrpStartDeviceWorker
04 nt!ExpWorkerThread
05 nt!PspSystemThreadStartup
06 nt!KiThreadStartup
1: kd> dv
AcpiObject = 0x8996e010
CompletionHandler = 0xf73fa3e2
CompletionContext = 0xf78f2cf4
Result = 0xf78f2d0b ""
1: kd> dt AMLISUPP_CONTEXT_PASSIVE 0xf78f2cf4 重要数值:
ACPI!AMLISUPP_CONTEXT_PASSIVE
+0x000 Event :_KEVENT
+0x010 Status : 0n-1073741275
1: kd> dx -id 0,0,899a2278 -r1 (*((ACPI!_KEVENT *)0xf78f2cf4))
(*((ACPI!_KEVENT *)0xf78f2cf4)) [Type: _KEVENT]
+0x000\] Header \[Type: _DISPATCHER_HEADER
1: kd> dx -id 0,0,899a2278 -r1 (*((ACPI!_DISPATCHER_HEADER *)0xf78f2cf4))
(*((ACPI!_DISPATCHER_HEADER *)0xf78f2cf4)) [Type: _DISPATCHER_HEADER]
+0x000\] Type : 0x1 \[Type: unsigned char
+0x001\] Absolute : 0x56 \[Type: unsigned char
+0x002\] Size : 0x4 \[Type: unsigned char
+0x003\] Inserted : 0x89 \[Type: unsigned char
+0x003\] DebugActive : 0x89 \[Type: unsigned char
+0x000\] Lock : -1996204543 \[Type: long
+0x004\] SignalState : 0 \[Type: long
+0x008\] WaitListHead \[Type: _LIST_ENTRY
1: kd> ?0n-1073741275
Evaluate expression: -1073741275 = c0000225
RtlZeroMemory(state, sizeof(IS_PCI_BUS_STATE));
state->AcpiObject = AcpiObject;
state->CompletionHandler = CompletionHandler;
state->CompletionContext = CompletionContext;
state->Result = Result;
state->RunCompletion = INITIAL_RUN_COMPLETION;
*Result = FALSE;
return IsPciBusAsyncWorker(AcpiObject,
STATUS_SUCCESS,
NULL,
(PVOID)state);
event在:IS_PCI_BUS_STATE state->CompletionContext = CompletionContext;
1: kd> t
eax=f78f2d0b ebx=00000000 ecx=8996e010 edx=899c5218 esi=804edc6c edi=899c5280
eip=f740dab7 esp=f78f2cb0 ebp=f78f2cb8 iopl=0 nv up ei ng nz na pe nc
cs=0008 ss=0010 ds=0023 es=0023 fs=0030 gs=0000 efl=00000286
ACPI!IsPciBusAsyncWorker+0x5:
f740dab7 8b7514 mov esi,dword ptr [ebp+14h] ss:0010:f78f2ccc=899c5218
1: kd> kc
00 ACPI!IsPciBusAsyncWorker
01 ACPI!IsPciBusAsync
02 ACPI!IsNsobjPciBus
03 ACPI!EnableDisableRegions
04 ACPI!ACPIFilterIrpStartDeviceWorker
05 nt!ExpWorkerThread
06 nt!PspSystemThreadStartup
07 nt!KiThreadStartup
1: kd> dv
AcpiObject = 0x8996e010
Status = 0n0
Result = 0x00000000
Context = 0x899c5218
status = 0n-1986244072
1: kd> dt IS_PCI_BUS_STATE 0x899c5218
ACPI!IS_PCI_BUS_STATE
+0x000 AcpiObject : 0x8996e010 _NSObj
+0x004 Flags : 0
+0x008 Hid : (null)
+0x00c Cid : (null)
+0x010 Adr : 0
+0x014 IsPciDevice : 0 ''
+0x018 RunCompletion : 0n-1
+0x01c CompletionHandler : 0xf73fa3e2 void ACPI!AmlisuppCompletePassive+0
+0x020 CompletionContext : 0xf78f2cf4 Void
+0x024 Result : 0xf78f2d0b ""
+0x028 Buffer : [64] ""
if (!(state->Flags & PCISUPP_CHECKED_PCI_DEVICE)) {
state->Flags |= PCISUPP_CHECKED_PCI_DEVICE;
status = IsPciDevice(state->AcpiObject,
IsPciBusAsyncWorker,
(PVOID)state, 第三个参数里面有event
&state->IsPciDevice);
1: kd> kc
00 ACPI!IsPciDevice
01 ACPI!IsPciBusAsyncWorker
02 ACPI!IsPciBusAsync
03 ACPI!IsNsobjPciBus
04 ACPI!EnableDisableRegions
05 ACPI!ACPIFilterIrpStartDeviceWorker
06 nt!ExpWorkerThread
07 nt!PspSystemThreadStartup
08 nt!KiThreadStartup
1: kd> dv
AcpiObject = 0x8996e010
CompletionHandler = 0xf740dab2
CompletionContext = 0x899c5218
Result = 0x899c522c ""
0xf78f2cf4
0x899c5218
RtlZeroMemory(state, sizeof(IS_PCI_DEVICE_STATE));
state->AcpiObject = AcpiObject;
state->CompletionHandler = CompletionHandler;
state->CompletionContext = CompletionContext;
state->Result = Result;
state->RunCompletion = INITIAL_RUN_COMPLETION;
return IsPciDeviceWorker(AcpiObject,
STATUS_SUCCESS,
NULL,
(PVOID)state);
1: kd> kc
00 ACPI!IsPciDeviceWorker
01 ACPI!IsPciDevice
02 ACPI!IsPciBusAsyncWorker
03 ACPI!IsPciBusAsync
04 ACPI!IsNsobjPciBus
05 ACPI!EnableDisableRegions
06 ACPI!ACPIFilterIrpStartDeviceWorker
07 nt!ExpWorkerThread
08 nt!PspSystemThreadStartup
09 nt!KiThreadStartup
1: kd> dv
AcpiObject = 0x8996e010
Status = 0n0
Result = 0x00000000
Context = 0x89909b70
0xf78f2cf4 AMLISUPP_CONTEXT_PASSIVE
0x899c5218 IS_PCI_BUS_STATE
0x89909b70 IS_PCI_DEVICE_STATE
//
// Step 3), check the _ADR.
//
if (!(state->Flags & PCISUPP_CHECKED_ADR)) {
state->Flags |= PCISUPP_CHECKED_ADR;
status = ACPIGetNSAddressAsync(
state->AcpiObject,
IsPciDeviceWorker,
(PVOID)state,
&(state->Adr),
NULL);
1: kd> kc
00 ACPI!ACPIGet
01 ACPI!IsPciDeviceWorker
02 ACPI!IsPciDevice
03 ACPI!IsPciBusAsyncWorker
04 ACPI!IsPciBusAsync
05 ACPI!IsNsobjPciBus
06 ACPI!EnableDisableRegions
07 ACPI!ACPIFilterIrpStartDeviceWorker
08 nt!ExpWorkerThread
09 nt!PspSystemThreadStartup
0a nt!KiThreadStartup
ACPI!ACPIGet:
f74076b8 55 push ebp
1: kd> dv
Target = 0x8996e010
ObjectID = 0x5244415f
Flags = 0x48040402
SimpleArgument = 0x00000000
SimpleArgumentSize = 0
CallBackRoutine = 0xf740d146
CallBackContext = 0x89909b70 CallBackContext = 0x89909b70
Buffer = 0x89909b78
BufferSize = 0x00000000
0xf78f2cf4 AMLISUPP_CONTEXT_PASSIVE
0x899c5218 IS_PCI_BUS_STATE
0x89909b70 IS_PCI_DEVICE_STATE
request->Flags = Flags;
request->ObjectID = ObjectID;
request->DeviceExtension = deviceExtension;
request->AcpiObject = acpiObject;
request->CallBackRoutine = CallBackRoutine;
request->CallBackContext = CallBackContext;
request->Buffer = Buffer;
request->BufferSize = BufferSize;
1: kd> dt ACPI_GET_REQUEST 89968240
+0x000 Flags : 0x48040402
+0x000 UFlags : __unnamed
+0x004 ObjectID : 0x5244415f
+0x008 ListEntry : _LIST_ENTRY [ 0xf743b940 - 0x899ae300 ]
+0x010 DeviceExtension : (null)
+0x014 AcpiObject : 0x8996e010 _NSObj
+0x018 CallBackRoutine : 0xf740d146 void ACPI!IsPciDeviceWorker+0
+0x01c CallBackContext : 0x89909b70 Void
+0x020 Buffer : 0x89909b78 -> (null)
+0x024 BufferSize : (null)
+0x028 Status : 0n0
+0x02c ResultData : _ObjData
0xf78f2cf4 AMLISUPP_CONTEXT_PASSIVE
0x899c5218 IS_PCI_BUS_STATE
0x89909b70 IS_PCI_DEVICE_STATE
89968240 ACPI_GET_REQUEST
KeAcquireSpinLock( &AcpiGetLock, &oldIrql );
InsertTailList(
&(AcpiGetListEntry),
&(request->ListEntry)
);
1: kd> x acpi!AcpiGetListEntry
f743b940 ACPI!AcpiGetListEntry = struct _LIST_ENTRY [ 0x899ae300 - 0x89968248 ]
1: kd> dx -r1 (*((ACPI!_LIST_ENTRY *)0xf743b940))
(*((ACPI!_LIST_ENTRY *)0xf743b940)) [Type: _LIST_ENTRY]
+0x000\] Flink : 0x899ae300 \[Type: _LIST_ENTRY \*
+0x004\] Blink : 0x89968248 \[Type: _LIST_ENTRY \*\] 这个: // // What we do now depends on wether or not the user wants us to // behave async or sync // if (async) { // // Evaluate the request // status = AMLIAsyncEvalObject( acpiObject, \&(request-\>ResultData), argumentCount, argumentPtr, completionRoutine, **request** 第六个参数最后一个参数: ); NTSTATUS AMLIAPI AMLIAsyncEvalObject(PNSOBJ pns, POBJDATA pdataResult, int icArgs, POBJDATA pdataArgs, PFNACB pfnAsyncCallBack, PVOID pvContext) 最后一个参数:pvContext重要 rc = AsyncEvalObject(pns, pdataResult, icArgs, pdataArgs, pfnAsyncCallBack, pvContext, TRUE); 1: kd\> kc # 00 ACPI!AsyncEvalObject 01 ACPI!AMLIAsyncEvalObject 02 ACPI!ACPIGet 03 ACPI!IsPciDeviceWorker 04 ACPI!IsPciDevice 05 ACPI!IsPciBusAsyncWorker 06 ACPI!IsPciBusAsync 07 ACPI!IsNsobjPciBus 08 ACPI!EnableDisableRegions 09 ACPI!ACPIFilterIrpStartDeviceWorker 0a nt!ExpWorkerThread 0b nt!PspSystemThreadStartup 0c nt!KiThreadStartup 1: kd\> dv pns = 0x8996e054 pdataResult = 0x8996826c icArgs = 0n0 pdataArgs = 0x00000000 pfnAsyncCallBack = 0xf7407364 **pvContext = 0x89968240** fAsync = 0x01 '' pctxt = 0x00000008 pfnAsyncCallBack = 0xf7407364 重要。记住。 1: kd\> u f7407364 ACPI!ACPIGetWorkerForInteger \[d:\\srv03rtm\\base\\busdrv\\acpi\\driver\\nt\\get.c @ 4707\]: f7407364 55 push ebp f7407365 8bec mov ebp,esp f7407367 51 push ecx f7407368 53 push ebx f7407369 8b5d0c mov ebx,dword ptr \[ebp+0Ch
f740736c 85db test ebx,ebx
f740736e 56 push esi
f740736f 57 push edi
0xf78f2cf4 AMLISUPP_CONTEXT_PASSIVE
0x899c5218 IS_PCI_BUS_STATE
0x89909b70 IS_PCI_DEVICE_STATE
89968240 ACPI_GET_REQUEST
if ((rc = NewContext(&pctxt)) == STATUS_SUCCESS)
{
BOOLEAN fQueueContext = FALSE;
pctxt->pnsObj = pns;
pctxt->pnsScope = pns;
pctxt->pfnAsyncCallBack = pfnAsyncCallBack;
pctxt->pdataCallBack = pdataResult;
pctxt->pvContext = pvContext; 至关重要:这里把信息放入了_ctxt结构!!!
if (pns->ObjData.dwDataType == OBJTYPE_METHOD)
{
if ((rc = PushCall(pctxt, pns, &pctxt->Result)) == STATUS_SUCCESS)
{
1: kd> dv
pctxt = 0x895c6000
pfnPost = 0xf741ef2b
uipData1 = 0x8996e054
uipData2 = 0
pdataResult = 0x895c6040
ppost = 0x00000008
rc = 0n-146681746
1: kd> dt ACPI!_ctxt 0x895c6000
+0x000 dwSig : 0x54585443
+0x004 pbCtxtEnd : 0x895c8000 ""
+0x008 listCtxt : _List
+0x010 listQueue : _List
+0x018 pplistCtxtQueue : (null)
+0x01c plistResources : (null)
+0x020 dwfCtxt : 0x100
+0x024 pnsObj : 0x8996e054 _NSObj
+0x028 pnsScope : 0x8996e054 _NSObj
+0x02c powner : (null)
+0x030 pcall : (null)
+0x034 pnctxt : (null)
+0x038 dwSyncLevel : 0
+0x03c pbOp : (null)
+0x040 Result : _ObjData
+0x054 pfnAsyncCallBack : 0xf7407364 void ACPI!ACPIGetWorkerForInteger+0 关键位置2:
+0x058 pdataCallBack : 0x8996826c _ObjData
+0x05c pvContext : 0x89968240 Void 关键位置1:
+0x060 Timer : _KTIMER
+0x088 Dpc : _KDPC
+0x0a8 pheapCurrent : 0x895c60bc _heap
+0x0ac CtxtData : _ctxtdata
+0x0bc LocalHeap : _heap
1: kd> kc
00 ACPI!PushPost
01 ACPI!AsyncEvalObject
02 ACPI!AMLIAsyncEvalObject
03 ACPI!ACPIGet
04 ACPI!IsPciDeviceWorker
05 ACPI!IsPciDevice
06 ACPI!IsPciBusAsyncWorker
07 ACPI!IsPciBusAsync
08 ACPI!IsNsobjPciBus
09 ACPI!EnableDisableRegions
0a ACPI!ACPIFilterIrpStartDeviceWorker
0b nt!ExpWorkerThread
0c nt!PspSystemThreadStartup
0d nt!KiThreadStartup
0xf78f2cf4 AMLISUPP_CONTEXT_PASSIVE
0x899c5218 IS_PCI_BUS_STATE
0x89909b70 IS_PCI_DEVICE_STATE
89968240 ACPI_GET_REQUEST
0x895c6000 _ctxt
1: kd> dv
pctxt = 0x895c6000
pfnPost = 0xf741ef2b
uipData1 = 0x8996e054
uipData2 = 0
pdataResult = 0x895c6040
ppost = 0x895c6040
rc = 0n-1990434752
1: kd> u f741ef2b
ACPI!ProcessEvalObj [d:\srv03rtm\base\busdrv\acpi\driver\amlinew\sync.c @ 546]:
f741ef2b 55 push ebp
f741ef2c 8bec mov ebp,esp
f741ef2e 53 push ebx
f741ef2f 56 push esi
f741ef30 57 push edi
f741ef31 6a01 push 1
f741ef33 be903043f7 mov esi,offset ACPI!`string' (f7433090)
f741ef38 56 push esi
1: kd> gu
eax=00000000 ebx=8996e054 ecx=8996e054 edx=895c7fe4 esi=f7438ca8 edi=f78f2b94
eip=f741fb1c esp=f78f2b88 ebp=f78f2bb0 iopl=0 nv up ei pl zr na pe nc
cs=0008 ss=0010 ds=0023 es=0023 fs=0030 gs=0000 efl=00000246
ACPI!AsyncEvalObject+0x253:
f741fb1c 8bf8 mov edi,eax
1: kd> dt ACPI!_ctxt 0x895c6000
+0x000 dwSig : 0x54585443
+0x004 pbCtxtEnd : 0x895c8000 ""
+0x008 listCtxt : _List
+0x010 listQueue : _List
+0x018 pplistCtxtQueue : (null)
+0x01c plistResources : (null)
+0x020 dwfCtxt : 0x100
+0x024 pnsObj : 0x8996e054 _NSObj
+0x028 pnsScope : 0x8996e054 _NSObj
+0x02c powner : (null)
+0x030 pcall : (null)
+0x034 pnctxt : (null)
+0x038 dwSyncLevel : 0
+0x03c pbOp : (null)
+0x040 Result : _ObjData
+0x054 pfnAsyncCallBack : 0xf7407364 void ACPI!ACPIGetWorkerForInteger+0
+0x058 pdataCallBack : 0x8996826c _ObjData
+0x05c pvContext : 0x89968240 Void
+0x060 Timer : _KTIMER
+0x088 Dpc : _KDPC
+0x0a8 pheapCurrent : 0x895c60bc _heap
+0x0ac CtxtData : _ctxtdata
+0x0bc LocalHeap : _heap
1: kd> dx -id 0,0,899a2278 -r1 (*((ACPI!_heap *)0x895c60bc))
(*((ACPI!_heap *)0x895c60bc)) [Type: _heap]
+0x000\] dwSig : 0x50414548 \[Type: unsigned long
+0x004\] pbHeapEnd : 0x895c7fe4 : 0x50 \[Type: unsigned char \*
+0x008\] pheapHead : 0x895c60bc \[Type: _heap \*
+0x00c\] pheapNext : 0x0 \[Type: _heap \*
+0x010\] pbHeapTop : 0x895c60d4 : 0x0 \[Type: unsigned char \*
+0x014\] plistFreeHeap : 0x0 \[Type: _List \*
+0x018\] Heap \[Type: _heapobjhdr
1: kd> dt _post 0x895c7fe4
ACPI!_post
+0x000 FrameHdr : _framehdr
+0x010 uipData1 : 0x8996e054
+0x014 uipData2 : 0
+0x018 pdataResult : 0x895c6040 _ObjData
1: kd> dx -id 0,0,899a2278 -r1 (*((ACPI!_framehdr *)0x895c7fe4))
(*((ACPI!_framehdr *)0x895c7fe4)) [Type: _framehdr]
+0x000\] dwSig : 0x54534f50 \[Type: unsigned long
+0x004\] dwLen : 0x1c \[Type: unsigned long
+0x008\] dwfFrame : 0x0 \[Type: unsigned long
+0x00c\] pfnParse : 0xf741ef2b \[Type: long (__cdecl\*)(_ctxt \*,void \*,long)
1: kd> u f741ef2b
ACPI!ProcessEvalObj [d:\srv03rtm\base\busdrv\acpi\driver\amlinew\sync.c @ 546]:
f741ef2b 55 push ebp
f741ef2c 8bec mov ebp,esp
f741ef2e 53 push ebx
f741ef2f 56 push esi
f741ef30 57 push edi
f741ef31 6a01 push 1
f741ef33 be903043f7 mov esi,offset ACPI!`string' (f7433090)
f741ef38 56 push esi
if (fQueueContext)
{
rc = RestartContext(pctxt, FALSE);
}
1: kd> kc
00 ACPI!RestartContext
01 ACPI!AsyncEvalObject
02 ACPI!AMLIAsyncEvalObject
03 ACPI!ACPIGet
04 ACPI!IsPciDeviceWorker
05 ACPI!IsPciDevice
06 ACPI!IsPciBusAsyncWorker
07 ACPI!IsPciBusAsync
08 ACPI!IsNsobjPciBus
09 ACPI!EnableDisableRegions
0a ACPI!ACPIFilterIrpStartDeviceWorker
0b nt!ExpWorkerThread
0c nt!PspSystemThreadStartup
0d nt!KiThreadStartup
1: kd> dv
pctxt = 0x895c6000
fDelayExecute = 0x00 ''
if (KeGetCurrentIrql() < DISPATCH_LEVEL)
{
AcquireMutex(&gReadyQueue.mutCtxtQ); 信息放入了acpi!gReadyQueue!!!
rc = InsertReadyQueue(pctxt, fDelayExecute);
ReleaseMutex(&gReadyQueue.mutCtxtQ);
}
1: kd> kc
00 ACPI!InsertReadyQueue
01 ACPI!RestartContext
02 ACPI!AsyncEvalObject
03 ACPI!AMLIAsyncEvalObject
04 ACPI!ACPIGet
05 ACPI!IsPciDeviceWorker
06 ACPI!IsPciDevice
07 ACPI!IsPciBusAsyncWorker
08 ACPI!IsPciBusAsync
09 ACPI!IsNsobjPciBus
0a ACPI!EnableDisableRegions
0b ACPI!ACPIFilterIrpStartDeviceWorker
0c nt!ExpWorkerThread
0d nt!PspSystemThreadStartup
0e nt!KiThreadStartup
1: kd> dv
pctxt = 0x895c6000
fDelayExecute = 0x00 ''
0xf78f2cf4 AMLISUPP_CONTEXT_PASSIVE
0x899c5218 IS_PCI_BUS_STATE
0x89909b70 IS_PCI_DEVICE_STATE
89968240 ACPI_GET_REQUEST
0x895c6000 _ctxt
//
// Make this context ready.
//
pctxt->dwfCtxt |= CTXTF_READY;
1: kd> x acpi!gReadyQueue
f743a928 ACPI!gReadyQueue = struct _ctxtq
1: kd> dx -r1 (*((ACPI!_ctxtq *)0xf743a928))
(*((ACPI!_ctxtq *)0xf743a928)) [Type: _ctxtq]
+0x000\] dwfCtxtQ : 0x1 \[Type: unsigned long
+0x004\] pkthCurrent : 0x89981ca0 \[Type: _KTHREAD \*
+0x008\] pctxtCurrent : 0x898ae000 \[Type: _ctxt \*
+0x00c\] plistCtxtQ : 0x0 \[Type: _List \*
+0x010\] dwmsTimeSliceLength : 0x64 \[Type: unsigned long
+0x014\] dwmsTimeSliceInterval : 0x64 \[Type: unsigned long
+0x018\] pfnPauseCallback : 0x0 \[Type: void (__cdecl\*)(void \*)
+0x01c\] PauseCBContext : 0x0 \[Type: void \*
+0x020\] mutCtxtQ \[Type: _mutex
+0x028\] Timer \[Type: _KTIMER
+0x050\] DpcStartTimeSlice \[Type: _KDPC
+0x070\] DpcExpireTimeSlice \[Type: _KDPC
+0x090\] WorkItem \[Type: _WORK_QUEUE_ITEM
else
{
//
// Insert the context in the ready queue.
//
ASSERT(!(pctxt->dwfCtxt & (CTXTF_IN_READYQ | CTXTF_RUNNING)));
LOGSCHEDEVENT('QCTX', (ULONG_PTR)pctxt, (ULONG_PTR)
(pctxt->pnctxt? pctxt->pnctxt->pnsObj: pctxt->pnsObj),
(ULONG_PTR)pctxt->pbOp);
if (!(pctxt->dwfCtxt & CTXTF_IN_READYQ))
{
pctxt->dwfCtxt |= CTXTF_IN_READYQ;
ListInsertTail(&pctxt->listQueue, &gReadyQueue.plistCtxtQ);
pctxt->pplistCtxtQueue = &gReadyQueue.plistCtxtQ;
}
1: kd> dx -r1 (*((ACPI!_ctxtq *)0xf743a928))
(*((ACPI!_ctxtq *)0xf743a928)) [Type: _ctxtq]
+0x000\] dwfCtxtQ : 0x1 \[Type: unsigned long
+0x004\] pkthCurrent : 0x89981ca0 \[Type: _KTHREAD \*
+0x008\] pctxtCurrent : 0x898ae000 \[Type: _ctxt \*
[+0x00c] plistCtxtQ : 0x895c6010 [Type: _List *] [+0x00c] plistCtxtQ : 0x895c6010
+0x010\] dwmsTimeSliceLength : 0x64 \[Type: unsigned long
+0x014\] dwmsTimeSliceInterval : 0x64 \[Type: unsigned long
+0x018\] pfnPauseCallback : 0x0 \[Type: void (__cdecl\*)(void \*)
+0x01c\] PauseCBContext : 0x0 \[Type: void \*
+0x020\] mutCtxtQ \[Type: _mutex
+0x028\] Timer \[Type: _KTIMER
+0x050\] DpcStartTimeSlice \[Type: _KDPC
+0x070\] DpcExpireTimeSlice \[Type: _KDPC
+0x090\] WorkItem \[Type: _WORK_QUEUE_ITEM
0xf78f2cf4 AMLISUPP_CONTEXT_PASSIVE
0x899c5218 IS_PCI_BUS_STATE
0x89909b70 IS_PCI_DEVICE_STATE
89968240 ACPI_GET_REQUEST
0x895c6000 _ctxt
f743a928 _ctxtq
1: kd> dt ACPI!_ctxt 0x895c6000
+0x000 dwSig : 0x54585443
+0x004 pbCtxtEnd : 0x895c8000 ""
+0x008 listCtxt : _List
+0x010 listQueue : _List
+0x018 pplistCtxtQueue : 0xf743a934 -> 0x895c6010 _List 关键地方:
+0x01c plistResources : (null)
+0x020 dwfCtxt : 0x148
+0x024 pnsObj : 0x8996e054 _NSObj
+0x028 pnsScope : 0x8996e054 _NSObj
+0x02c powner : (null)
+0x030 pcall : (null)
+0x034 pnctxt : (null)
+0x038 dwSyncLevel : 0
+0x03c pbOp : (null)
+0x040 Result : _ObjData
+0x054 pfnAsyncCallBack : 0xf7407364 void ACPI!ACPIGetWorkerForInteger+0
+0x058 pdataCallBack : 0x8996826c _ObjData
+0x05c pvContext : 0x89968240 Void
+0x060 Timer : _KTIMER
+0x088 Dpc : _KDPC
+0x0a8 pheapCurrent : 0x895c60bc _heap
+0x0ac CtxtData : _ctxtdata
+0x0bc LocalHeap : _heap
pctxt->dwfCtxt |= CTXTF_NEED_CALLBACK; 需要回调!
rc = AMLISTA_PENDING;
}
status = IsPciDevice(state->AcpiObject,
IsPciBusAsyncWorker,
(PVOID)state,
&state->IsPciDevice);
if (status == STATUS_PENDING) {
return status;
}
1: kd> kc
00 ACPI!IsPciBusAsyncWorker
01 ACPI!IsPciBusAsync
02 ACPI!IsNsobjPciBus
03 ACPI!EnableDisableRegions
04 ACPI!ACPIFilterIrpStartDeviceWorker
05 nt!ExpWorkerThread
06 nt!PspSystemThreadStartup
07 nt!KiThreadStartup
status = IsPciBusAsync( Device,
AmlisuppCompletePassive,
(PVOID)&getDataContext,
&result );
if (status == STATUS_PENDING) {
KeWaitForSingleObject(&getDataContext.Event,
Executive,
KernelMode,
FALSE,
NULL);
status = getDataContext.Status;
}
1: kd> p
Breakpoint 13 hit
eax=00000000 ebx=00000000 ecx=00000000 edx=80010031 esi=f78f2cf4 edi=00000103
eip=f73fa414 esp=f791ab50 ebp=f791ab54 iopl=0 nv up ei pl zr na pe nc
cs=0008 ss=0010 ds=0023 es=0023 fs=0030 gs=0000 efl=00000246
ACPI!AmlisuppCompletePassive+0x32:
f73fa414 5e pop esi
1: kd> kc
00 ACPI!AmlisuppCompletePassive
01 ACPI!IsPciBusAsyncWorker
02 ACPI!PciConfigSpaceHandlerWorker
03 ACPI!GetPciAddressWorker
04 ACPI!GetPciAddressWorker
05 ACPI!ACPIGetWorkerForInteger
06 ACPI!AsyncCallBack
07 ACPI!RunContext
08 ACPI!DispatchCtxtQueue
09 ACPI!StartTimeSlicePassive
0a ACPI!ACPIWorker
0b nt!PspSystemThreadStartup
0c nt!KiThreadStartup
1: kd> dv
AcpiObject = 0x8996dc38
Status = 0n0
Result = 0x00000000
Context = 0xf78f2cf4 0xf78f2cf4正确!!!
0xf78f2cf4 AMLISUPP_CONTEXT_PASSIVE
0x899c5218 IS_PCI_BUS_STATE
0x89909b70 IS_PCI_DEVICE_STATE
89968240 ACPI_GET_REQUEST
0x895c6000 _ctxt
f743a928 _ctxtq
第二大部分:解释为什么没有调用ACPI!OSQueueWorkItem开启worker线程。
1: kd> bl
0 e Disable Clear f74001de [d:\srv03rtm\base\busdrv\acpi\driver\nt\detect.c @ 1821] 0001 (0001) ACPI!ACPIDetectPdoDevices
1 d Enable Clear f74076b8 [d:\srv03rtm\base\busdrv\acpi\driver\nt\get.c @ 76] 0001 (0001) ACPI!ACPIGet
2 e Disable Clear f740cf7a [d:\srv03rtm\base\busdrv\acpi\driver\nt\pciopregion.c @ 1047] 0001 (0001) ACPI!GetPciAddressWorker+0x90
3 d Enable Clear f742051c [d:\srv03rtm\base\busdrv\acpi\driver\amlinew\sched.c @ 188] 0001 (0001) ACPI!InsertReadyQueue
4 d Enable Clear f742042d [d:\srv03rtm\base\busdrv\acpi\driver\amlinew\sched.c @ 150] 0001 (0001) ACPI!DispatchCtxtQueue+0xaf
5 e Disable Clear f741337f [d:\srv03rtm\base\busdrv\acpi\driver\nt\worker.c @ 279] 0001 (0001) ACPI!ACPIWorker+0x79
6 e Disable Clear 804f25ee [d:\srv03rtm\base\hals\halacpi\pmbus.c @ 165] 0001 (0001) hal!HalGetBusDataByOffset
7 e Disable Clear f7413470 [d:\srv03rtm\base\busdrv\acpi\driver\nt\worker.c @ 364] 0001 (0001) ACPI!OSQueueWorkItem
8 e Disable Clear f7420495 [d:\srv03rtm\base\busdrv\acpi\driver\amlinew\sched.c @ 93] 0001 (0001) ACPI!StartTimeSlicePassive
9 e Disable Clear f74133c5 [d:\srv03rtm\base\busdrv\acpi\driver\nt\worker.c @ 302] 0001 (0001) ACPI!ACPIWorker+0xbf
10 e Disable Clear f74486af [d:\srv03rtm\base\busdrv\acpi\driver\nt\pciopregion.c @ 1987] 0001 (0001) ACPI!IsNsobjPciBus+0x7f
11 e Disable Clear f73fa3e2 [d:\srv03rtm\base\busdrv\acpi\driver\nt\amlisupp.c @ 204] 0001 (0001) ACPI!AmlisuppCompletePassive
12 e Disable Clear 80a34206 [d:\srv03rtm\base\ntos\ke\eventobj.c @ 378] 0001 (0001) nt!KeSetEvent
13 e Disable Clear f73fa414 [d:\srv03rtm\base\busdrv\acpi\driver\nt\amlisupp.c @ 210] 0001 (0001) ACPI!AmlisuppCompletePassive+0x32
14 e Disable Clear f742037e [d:\srv03rtm\base\busdrv\acpi\driver\amlinew\sched.c @ 128] 0001 (0001) ACPI!DispatchCtxtQueue
15 e Disable Clear f7448630 [d:\srv03rtm\base\busdrv\acpi\driver\nt\pciopregion.c @ 1961] 0001 (0001) ACPI!IsNsobjPciBus
23 e Disable Clear u 0001 (0001) (authui!WluirRequestCredentials)
没有调用nt!KeSetEvent和ACPI!OSQueueWorkItem函数怎么
VOID
OSQueueWorkItem(
IN PWORK_QUEUE_ITEM WorkItem
)
{
KIRQL OldIrql;
ASSERT(KeGetCurrentIrql() <= DISPATCH_LEVEL);
//
// Insert the work item
//
KeAcquireSpinLock(&ACPIWorkerSpinLock, &OldIrql);
if (IsListEmpty(&ACPIWorkQueue)) {
KeSetEvent(&ACPIWorkToDoEvent, 0, FALSE);
}
InsertTailList(&ACPIWorkQueue, &WorkItem->List);
KeReleaseSpinLock(&ACPIWorkerSpinLock, OldIrql);
return;
}
F:\srv03rtm>grep "ACPIWorkToDoEvent" -nr F:\srv03rtm\base\busdrv\acpi |grep -v "inary"
F:\srv03rtm\base\busdrv\acpi/driver/nt/obj/i386/acpi.map:2960: 0003:00003330 _ACPIWorkToDoEvent 00052330 <common>
F:\srv03rtm\base\busdrv\acpi/driver/nt/worker.c:15:KEVENT ACPIWorkToDoEvent;
F:\srv03rtm\base\busdrv\acpi/driver/nt/worker.c:53: KeInitializeEvent(&ACPIWorkToDoEvent, NotificationEvent, FALSE);
F:\srv03rtm\base\busdrv\acpi/driver/nt/worker.c:228: WaitObjects[ACPIWorkToDo] = (PVOID)&ACPIWorkToDoEvent;
F:\srv03rtm\base\busdrv\acpi/driver/nt/worker.c:282: KeClearEvent(&ACPIWorkToDoEvent);
F:\srv03rtm\base\busdrv\acpi/driver/nt/worker.c:374: KeSetEvent(&ACPIWorkToDoEvent, 0, FALSE);
VOID LOCAL DispatchCtxtQueue(PCTXTQ pctxtq)
{
TRACENAME("DISPATCHCTXTQUEUE")
LARGE_INTEGER liTimeout;
PLIST plist;
PCTXT pctxt;
ENTER(2, ("DispatchCtxtQueue(pctxtq=%x)\n", pctxtq));
ASSERT((pctxtq->plistCtxtQ != NULL) && (pctxtq->pkthCurrent == NULL));
liTimeout.QuadPart = (INT_PTR)(-10000*(INT_PTR)pctxtq->dwmsTimeSliceLength);
pctxtq->dwfCtxtQ &= ~CQF_TIMESLICE_EXPIRED;
KeSetTimer(&pctxtq->Timer, liTimeout, &pctxtq->DpcExpireTimeSlice);
while ((plist = ListRemoveHead(&pctxtq->plistCtxtQ)) != NULL) 这里会循环检查acpi!gReadyQueue是否有上下文需要处理
{
pctxt = CONTAINING_RECORD(plist, CTXT, listQueue);
ASSERT(pctxt->pplistCtxtQueue == &pctxtq->plistCtxtQ);
pctxt->pplistCtxtQueue = NULL;
pctxt->dwfCtxt &= ~CTXTF_IN_READYQ;
RunContext(pctxt);
}
else if ((gReadyQueue.pkthCurrent == NULL) &&
!(gReadyQueue.dwfCtxtQ & CQF_PAUSED))
//
// We only execute the method if we are not in paused state.
// 如果gReadyQueue.pkthCurrent的当前上线文没有则需要OSQueueWorkItem开启线程
{
LOGSCHEDEVENT('EVAL', (ULONG_PTR)pctxt, (ULONG_PTR)
(pctxt->pnctxt? pctxt->pnctxt->pnsObj: pctxt->pnsObj),
(ULONG_PTR)pctxt->pbOp);
//
// There is no active context and we can execute it immediately.
//
rc = RunContext(pctxt);
if ((gReadyQueue.plistCtxtQ != NULL) &&
!(gReadyQueue.dwfCtxtQ & CQF_WORKITEM_SCHEDULED))
{
//
// If we have more jobs in the queue and we haven't scheduled
// a dispatch, schedule one.
//
LOGSCHEDEVENT('KICK', (ULONG_PTR)rc, 0, 0);
OSQueueWorkItem(&gReadyQueue.WorkItem);
gReadyQueue.dwfCtxtQ |= CQF_WORKITEM_SCHEDULED;
}
}
else //如果gReadyQueue.pkthCurrent的当前上线文有则不需要调用OSQueueWorkItem开启线程
{ 直接添加进acpi!gReadyQueue,因为DispatchCtxtQueue函数会循环检查上下文!!!
//
// Insert the context in the ready queue.
//
ASSERT(!(pctxt->dwfCtxt & (CTXTF_IN_READYQ | CTXTF_RUNNING)));
LOGSCHEDEVENT('QCTX', (ULONG_PTR)pctxt, (ULONG_PTR)
(pctxt->pnctxt? pctxt->pnctxt->pnsObj: pctxt->pnsObj),
(ULONG_PTR)pctxt->pbOp);
if (!(pctxt->dwfCtxt & CTXTF_IN_READYQ))
{
pctxt->dwfCtxt |= CTXTF_IN_READYQ;
ListInsertTail(&pctxt->listQueue, &gReadyQueue.plistCtxtQ);
pctxt->pplistCtxtQueue = &gReadyQueue.plistCtxtQ;
}
pctxt->dwfCtxt |= CTXTF_NEED_CALLBACK;
rc = AMLISTA_PENDING;
}
1: kd> dx -r1 (*((ACPI!_ctxtq *)0xf743a928))
(*((ACPI!_ctxtq *)0xf743a928)) [Type: _ctxtq]
+0x000\] dwfCtxtQ : 0x1 \[Type: unsigned long
+0x004\] pkthCurrent : 0x89981ca0 \[Type: _KTHREAD \*
+0x008\] pctxtCurrent : 0x898ae000 \[Type: _ctxt \*
+0x00c\] plistCtxtQ : 0x895c6010 \[Type: _List \*
+0x010\] dwmsTimeSliceLength : 0x64 \[Type: unsigned long
+0x014\] dwmsTimeSliceInterval : 0x64 \[Type: unsigned long
+0x018\] pfnPauseCallback : 0x0 \[Type: void (__cdecl\*)(void \*)
+0x01c\] PauseCBContext : 0x0 \[Type: void \*
+0x020\] mutCtxtQ \[Type: _mutex
+0x028\] Timer \[Type: _KTIMER
+0x050\] DpcStartTimeSlice \[Type: _KDPC
+0x070\] DpcExpireTimeSlice \[Type: _KDPC
+0x090\] WorkItem \[Type: _WORK_QUEUE_ITEM