2008년 08월 29일
Windbg를 이용한 IoCallDriver 분석
IoCallDriver는 파라미터를 받을 때 fastcall방식을 사용합니다.
즉, ecx는 첫번째 파라미터(DeviceObject), edx는 두번째 파라미터(Irp)가 입력됩니다.
lkd> u nt!IopfCallDriver
804e33a2 dec byte ptr [edx+23h] ; Irp->CurrentLocation 을 1 감소합니다.
; 즉 현재 스택에서 하위 스택으로 이동하는 것이지요
804e33a5 mov al,byte ptr [edx+23h]
804e33a8 test al,al
804e33aa jle nt!IopfCallDriver+0xa (805222e1); 현재 스택의 위치가 0보다 작다면
; nt!IopfCallDriver+0xa 로 점프합니다.
; u 명령어로 역어셈 해보니 블루스크린을 발생하는 곳이군요.
; 즉 현재 스택위치가 0보다 작다는 의미는
; 더이상 하위 스택이 없단 의미로 이렇게 되면 무엇인가
; 코드가 문제가 있는 것이니 더이상 진행할 수 없어 블루스크린을
; 띄우는 것입니다.
804e33b0 mov eax,dword ptr [edx+60h]
804e33b3 sub eax,24h; 이번엔 Irp->OverLay.CurrentStackLocation을 가져옵니다.
; CurrentStackLocation에서 -24를 하네요... 왜 -24를 뺄까요?
; 그것은 하위 스택의 주소를 가져오기 위함입니다.
; 스택의 자료구조는 _IO_STACK_LOCATION이고 이 구조체의
; 크기는 24입니다. 헤헤.. 네~ 포인터 연산을 하는 것입니다.
804e33b6 push esi
804e33b7 mov dword ptr [edx+60h],eax; 포인터 연산을 마무리하네요..
; 다음 스택을 Irp->Overlay.CurrentStackLocation에 설정합니다.
804e33ba mov dword ptr [eax+14h],ecx; nextStack->DeviceObject에 파라미터로 받은
; DeviceObject를 설정합니다.
804e33bd movzx eax,byte ptr [eax]; eax는 currentStack이었죠 첫번째 필드는 MajorFunction입니다.
804e33c0 mov esi,dword ptr [ecx+8] ; ecx는 DeviceObject이고 +8의 위치는 DriverObject를 뜻합니다.
804e33c3 push edx
804e33c4 push ecx
804e33c5 call dword ptr [esi+eax*4+38h]; DriverObject+ 38h + MajorFunction*4 라는 뜻이 되겠네요.
; DriverObject+ 38h는 MajorFunction Table을 뜻합니다.
; 즉 DriverObject에 MajorFunction에 해당하는 함수를 호출하는 것이 되겠네요.
804e33c9 pop esi
804e33ca ret
lkd> u 805222e1
nt!IopfCallDriver+0xa:
805222e1 push 0
805222e3 push 0
805222e5 push 0
805222e7 push edx
805222e8 push 35h
805222ea call nt!KeBugCheckEx (80539657) ; 블루스크린을 발생시킵니다.!
805222ef mov esi,dword ptr [eax+4]위의 코드를 보면 IoCallDriver의 역할은 Irp를 하위 스택으로 설정하고
하위 스택의 DriverObject의 MajorFunction에 대한 함수를 호출하는 것으로
정리할 수 있습니다.
p.s. 밑의 자료구조와 매칭해서 보시면 더욱 이해가 쉬울 것입니다.lkd> dt _IRP
nt!_IRP
+0x000 Type : Int2B
+0x002 Size : Uint2B
+0x004 MdlAddress : Ptr32 _MDL
+0x008 Flags : Uint4B
+0x00c AssociatedIrp : __unnamed
+0x010 ThreadListEntry : _LIST_ENTRY
+0x018 IoStatus : _IO_STATUS_BLOCK
+0x020 RequestorMode : Char
+0x021 PendingReturned : UChar
+0x022 StackCount : Char
+0x023 CurrentLocation : Char
+0x024 Cancel : UChar
+0x025 CancelIrql : UChar
+0x026 ApcEnvironment : Char
+0x027 AllocationFlags : UChar
+0x028 UserIosb : Ptr32 _IO_STATUS_BLOCK
+0x02c UserEvent : Ptr32 _KEVENT
+0x030 Overlay : __unnamed
+0x038 CancelRoutine : Ptr32 void
+0x03c UserBuffer : Ptr32 Void
+0x040 Tail : __unnamed
+0x000 Overlay : __unnamed
+0x000 DeviceQueueEntry : _KDEVICE_QUEUE_ENTRY
+0x000 DriverContext : [4] Ptr32 Void
+0x010 Thread : Ptr32 _ETHREAD
+0x014 AuxiliaryBuffer : Ptr32 Char
+0x018 ListEntry : _LIST_ENTRY
+0x020 CurrentStackLocation : Ptr32 _IO_STACK_LOCATION
+0x020 PacketType : Uint4B
+0x024 OriginalFileObject : Ptr32 _FILE_OBJECT
lkd> dt _IO_STACK_LOCATION
nt!_IO_STACK_LOCATION
+0x000 MajorFunction : UChar
+0x001 MinorFunction : UChar
+0x002 Flags : UChar
+0x003 Control : UChar
+0x004 Parameters : __unnamed
+0x014 DeviceObject : Ptr32 _DEVICE_OBJECT
+0x018 FileObject : Ptr32 _FILE_OBJECT
+0x01c CompletionRoutine : Ptr32 long
+0x020 Context : Ptr32 Void
lkd> dt _DEVICE_OBJECT
nt!_DEVICE_OBJECT
+0x000 Type : Int2B
+0x002 Size : Uint2B
+0x004 ReferenceCount : Int4B
+0x008 DriverObject : Ptr32 _DRIVER_OBJECT
+0x00c NextDevice : Ptr32 _DEVICE_OBJECT
+0x010 AttachedDevice : Ptr32 _DEVICE_OBJECT
+0x014 CurrentIrp : Ptr32 _IRP
+0x018 Timer : Ptr32 _IO_TIMER
+0x01c Flags : Uint4B
+0x020 Characteristics : Uint4B
+0x024 Vpb : Ptr32 _VPB
+0x028 DeviceExtension : Ptr32 Void
+0x02c DeviceType : Uint4B
+0x030 StackSize : Char
+0x034 Queue : __unnamed
+0x05c AlignmentRequirement : Uint4B
+0x060 DeviceQueue : _KDEVICE_QUEUE
+0x074 Dpc : _KDPC
+0x094 ActiveThreadCount : Uint4B
+0x098 SecurityDescriptor : Ptr32 Void
+0x09c DeviceLock : _KEVENT
+0x0ac SectorSize : Uint2B
+0x0ae Spare1 : Uint2B
+0x0b0 DeviceObjectExtension : Ptr32 _DEVOBJ_EXTENSION
+0x0b4 Reserved : Ptr32 Void
lkd> dt _DRIVER_OBJECT
nt!_DRIVER_OBJECT
+0x000 Type : Int2B
+0x002 Size : Int2B
+0x004 DeviceObject : Ptr32 _DEVICE_OBJECT
+0x008 Flags : Uint4B
+0x00c DriverStart : Ptr32 Void
+0x010 DriverSize : Uint4B
+0x014 DriverSection : Ptr32 Void
+0x018 DriverExtension : Ptr32 _DRIVER_EXTENSION
+0x01c DriverName : _UNICODE_STRING
+0x024 HardwareDatabase : Ptr32 _UNICODE_STRING
+0x028 FastIoDispatch : Ptr32 _FAST_IO_DISPATCH
+0x02c DriverInit : Ptr32 long
+0x030 DriverStartIo : Ptr32 void
+0x034 DriverUnload : Ptr32 void
+0x038 MajorFunction : [28] Ptr32 long
# by | 2008/08/29 09:58 | 트랙백 | 덧글(1)






☞ 내 이글루에 이 글과 관련된 글 쓰기 (트랙백 보내기) [도움말]