Skip to content

Latest commit

 

History

History
84 lines (79 loc) · 2.73 KB

200311231448.txt.md

File metadata and controls

84 lines (79 loc) · 2.73 KB
  1. ntdll!RtlGetProcessHeaps()

Hume(冷雨飘心)果然对SEH了解深入,以前我一直没有关注过__finally块,直到看见 Hume所给的RtlGetProcessHeaps()伪代码,奇怪Hume凭什么认为这里是__finally块, 而不是__except块,仔细研究了一番,佩服Hume!

原C风格的伪代码基本正确,但在表述__finally块范围时有误,另一处是返回值表述 有误,我修正如下,算是狗尾续貂:


/*

  • Create: Hume 2003-11-07 17:29
  • Modify: scz 2003-11-10 13:51
  •          2003-12-01 11:09
  • ntdll.dll中定义的全局变量 */ extern unsigned char RtlpDebugPageHeap; extern RTL_CRITICAL_SECTION RtlpProcessHeapsListLock;

DWORD __stdcall RtlGetProcessHeaps ( DWORD NumberOfHeaps, // maximum number of heap handles PHANDLE ProcessHeaps // buffer for heap handles ) { DWORD PebNumberOfHeaps; DWORD LocalNumberOfHeaps; PTEB Teb = NtCurrentTeb(); DWORD ret;

RtlEnterCriticalSection( &RtlpProcessHeapsListLock );
__try
{
    PebNumberOfHeaps    = Teb->Peb->NumberOfHeaps;
    if ( Teb->Peb->NumberOfHeaps > NumberOfHeaps )
    {
        LocalNumberOfHeaps  = NumberOfHeaps;
    }
    else
    {
        LocalNumberOfHeaps  = Teb->Peb->NumberOfHeaps;
    }
    /*
     * 这条语句可能引发异常,需要SEH机制的保护
     */
    CopyMemory
    (
        ProcessHeaps,
        Teb->Peb->ProcessHeaps,
        LocalNumberOfHeaps * sizeof( HANDLE )
    );
    /*
     * 修正形参,为处理调试堆做准备
     */
    ProcessHeaps       += LocalNumberOfHeaps * sizeof( HANDLE );
    NumberOfHeaps      -= LocalNumberOfHeaps;
}
__finally
{
    ret                 = PebNumberOfHeaps;
    RtlLeaveCriticalSection( &RtlpProcessHeapsListLock );
}
/*
 * 注意,后续代码不受本函数中的SEH机制保护,并且已经离开临界区。
 * RtlpDebugPageHeapGetProcessHeaps()有自己的SEH机制提供保护。
 */
if ( RtlpDebugPageHeap )
{
    ret += RtlpDebugPageHeapGetProcessHeaps
           (
               NumberOfHeaps,
               ProcessHeaps
           );
}
/*
 * The return value is the number of heap handles that are valid for
 * the calling process.
 *
 * 注意,这个返回值不是当前获取的堆句柄数,而是整个进程中有效堆句柄数。
 */
return( ret );

} /* end of RtlGetProcessHeaps */