ntdll!LdrpNameToOrdinal函数分析之二分查找
第一部分:
1: kd> t
ntdll!LdrpNameToOrdinal:
001b:77f28c72 55 push ebp
1: kd> kc
#
00 ntdll!LdrpNameToOrdinal
01 ntdll!LdrpSnapThunk
02 ntdll!LdrpGetProcedureAddress
03 ntdll!LdrGetProcedureAddress
04 ntdll!CsrClientConnectToServer
05 kernel32!BaseDllInitialize
06 ntdll!LdrpCallInitRoutine
07 ntdll!LdrpRunInitializeRoutines
08 ntdll!LdrpLoadDll
09 ntdll!LdrLoadDll
0a csrsrv!CsrLoadServerDll
0b csrsrv!CsrParseServerCommandLine
0c csrsrv!CsrServerInitialization
0d csrss!main
0e csrss!NtProcessStartup
1: kd> dv
Name = 0x0015f1ce "CsrCallServerFromServer"
NumberOfNames = 0x23
DllBase = 0x752a0000
NameTableBase = 0x752a9334
NameOrdinalTableBase = 0x752a93c0
Low = 0n1438156
第二部分:
1: kd> dd 0x752a9334
752a9334 00009411 0000942a 00009442 00009453
752a9344 00009464 0000947a 0000948a 00009498
752a9354 000094a8 000094bc 000094d2 000094e7
752a9364 000094fa 0000950c 0000951d 00009531
752a9374 00009543 00009558 00009571 00009589
752a9384 0000959e 000095ac 000095c2 000095d2
752a9394 000095e5 000095f5 0000960d 00009626
752a93a4 0000963b 00009654 00009669 00009685
1: kd> db 0x752a9411
752a9411 43 73 72 41 64 64 53 74-61 74 69 63 53 65 72 76 CsrAddStaticServ
752a9421 65 72 54 68 72 65 61 64-00 43 73 72 43 61 6c 6c erThread.CsrCall
752a9431 53 65 72 76 65 72 46 72-6f 6d 53 65 72 76 65 72 ServerFromServer
752a9441 00 43 73 72 43 6f 6e 6e-65 63 74 54 6f 55 73 65 .CsrConnectToUse
752a9451 72 00 43 73 72 43 72 65-61 74 65 50 72 6f 63 65 r.CsrCreateProce
752a9461 73 73 00 43 73 72 43 72-65 61 74 65 52 65 6d 6f ss.CsrCreateRemo
752a9471 74 65 54 68 72 65 61 64-00 43 73 72 43 72 65 61 teThread.CsrCrea
752a9481 74 65 54 68 72 65 61 64-00 43 73 72 43 72 65 61 teThread.CsrCrea
1: kd> dd 0x752a93c0
752a93c0 00010000 00030002 00050004 00070006
752a93d0 00090008 000b000a 000d000c 000f000e
752a93e0 00110010 00130012 00150014 00170016
752a93f0 00190018 001b001a 001d001c 001f001e
752a9400 00210020 53430022 56525352 6c6c642e
第三部分:
1: kd> dv
Name = 0x0015f1ce "CsrCallServerFromServer"
NumberOfNames = 0x23
DllBase = 0x752a0000
NameTableBase = 0x752a9334
NameOrdinalTableBase = 0x752a93c0
Low = 0n0
Low = 0;
Middle = 0;
High = NumberOfNames - 1;
while (High >= Low) {
//
// Compute the next probe index and compare the import name
// with the export name entry.
//
Middle = (Low + High) >> 1;
Result = strcmp(Name, (PCHAR)((ULONG_PTR)DllBase + NameTableBase[Middle]));
if (Result < 0) {
High = Middle - 1;
第四部分:
第一轮:Middle = (Low + High) >> 1=esi=00000011
1: kd> p
ntdll!LdrpNameToOrdinal+0x1d:
001b:77f28c8f d1fe sar esi,1
1: kd> p
ntdll!LdrpNameToOrdinal+0x1f:
001b:77f28c91 8b04b0 mov eax,dword ptr [eax+esi*4]
1: kd> r
eax=752a9334 ebx=0015f1ce ecx=00000022 edx=0015f143 esi=00000011
1: kd> p
ntdll!LdrpNameToOrdinal+0x49:
001b:77f28cbb 83d8ff sbb eax,0FFFFFFFFh
1: kd> p
ntdll!LdrpNameToOrdinal+0x4c:
001b:77f28cbe 85c0 test eax,eax
1: kd> r
eax=ffffffff ebx=0015f143 ecx=00000022 edx=0015f143 esi=00000011 edi=0015f1d0
eip=77f28cbe esp=0015f138 ebp=0015f148 iopl=0 nv up ei ng nz ac pe cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000297
ntdll!LdrpNameToOrdinal+0x4c:
001b:77f28cbe 85c0 test eax,eax
1: kd> bp 77f28cbe
Result=eax=ffffffff=-1
1: kd> p
ntdll!LdrpNameToOrdinal+0x50:
001b:77f28cc2 8d4eff lea ecx,[esi-1]
1: kd> p
ntdll!LdrpNameToOrdinal+0x53:
001b:77f28cc5 eb08 jmp ntdll!LdrpNameToOrdinal+0x5d (77f28ccf)
1: kd> r
eax=ffffffff ebx=0015f143 ecx=00000010 edx=0015f143 esi=00000011 edi=0015f1d0
ecx=00000010
High = Middle - 1=ecx=00000010
第二轮:Middle = (Low + High) >> 1=esi=00000008
1: kd> g
Breakpoint 13 hit
ntdll!LdrpNameToOrdinal+0x1f:
001b:77f28c91 8b04b0 mov eax,dword ptr [eax+esi*4]
1: kd> r
eax=752a9334 ebx=0015f143 ecx=00000010 edx=0015f143 esi=00000008 edi=0015f1ce
1: kd> g
Breakpoint 14 hit
ntdll!LdrpNameToOrdinal+0x4c:
001b:77f28cbe 85c0 test eax,eax
1: kd> r
eax=ffffffff
Result=eax=ffffffff=-1
1: kd> g
Breakpoint 15 hit
ntdll!LdrpNameToOrdinal+0x53:
001b:77f28cc5 eb08 jmp ntdll!LdrpNameToOrdinal+0x5d (77f28ccf)
1: kd> r
eax=ffffffff ebx=0015f143 ecx=00000007
High = Middle - 1=ecx=00000007
第三轮:Middle = (Low + High) >> 1=esi=00000003
1: kd> g
Breakpoint 13 hit
ntdll!LdrpNameToOrdinal+0x1f:
001b:77f28c91 8b04b0 mov eax,dword ptr [eax+esi*4]
1: kd> r
eax=752a9334 ebx=0015f143 ecx=00000007 edx=0015f143 esi=00000003
1: kd> g
Breakpoint 14 hit
ntdll!LdrpNameToOrdinal+0x4c:
001b:77f28cbe 85c0 test eax,eax
1: kd> r
eax=ffffffff
Result=eax=ffffffff=-1
1: kd> g
Breakpoint 15 hit
ntdll!LdrpNameToOrdinal+0x53:
001b:77f28cc5 eb08 jmp ntdll!LdrpNameToOrdinal+0x5d (77f28ccf)
1: kd> r
eax=ffffffff ebx=0015f161 ecx=00000002
High = Middle - 1=ecx=00000002
第四轮:Middle = (Low + High) >> 1=esi=00000001
1: kd> g
Breakpoint 13 hit
ntdll!LdrpNameToOrdinal+0x1f:
001b:77f28c91 8b04b0 mov eax,dword ptr [eax+esi*4]
1: kd> r
eax=752a9334 ebx=0015f161 ecx=00000002 edx=0015f161 esi=00000001
1: kd> g
Breakpoint 14 hit
ntdll!LdrpNameToOrdinal+0x4c:
001b:77f28cbe 85c0 test eax,eax
1: kd> r
eax=00000000
Result=eax=00000000
} else {
break;
}
}
第五部分:
IN PUSHORT NameOrdinalTableBase
if (High < Low) {
return (USHORT)-1;
} else {
return NameOrdinalTableBase[Middle];=0x0001
}
}
1: kd> dd 0x752a93c0
752a93c0 00010000 00030002 00050004 00070006
752a93d0 00090008 000b000a 000d000c 000f000e
752a93e0 00110010 00130012 00150014 00170016
752a93f0 00190018 001b001a 001d001c 001f001e
752a9400 00210020 53430022 56525352 6c6c642e