DelayedLoading (Delphi)

From RAD Studio XE2 Code Examples

Jump to: navigation, search

Language:

Versions:

Contents

Description

This example demonstrates the fine tuning of the delay loading mechanism. Using the provided functionality, one can hook-up various steps in the delay loading process. This example defines three cases, one of which is correct, and two incorrect.

Code

function GetDesktopWindow: HWND; stdcall; external user32 name 'GetDesktopWindow' delayed;
function GetFooBar: Integer; stdcall; external kernel32 name 'GetFooBar' delayed;
function GetFooBarBar: Integer; stdcall; external 'kernel33' name 'GetFooBarBar' delayed;
 
var
  LOldNotifyHook, LOldFailureHook: TDelayedLoadHook; { for storing the old hook pointers }
 
{ Utility function to retrieve the name of the imported routine or its ordinal }
function ImportName(const AProc: TDelayLoadProc): String; inline;
begin
  if AProc.fImportByName then
    Result := AProc.szProcName
  else
    Result := '#' + IntToStr(AProc.dwOrdinal);
end;
 
function MyDelayedLoadHook(dliNotify: dliNotification; pdli: PDelayLoadInfo): Pointer; stdcall;
begin
  { Write a message for each dli notification }
  case dliNotify of
    dliNoteStartProcessing:
      WriteLn('Started the delayed load session for "', pdli.szDll, '" DLL');
    dliNotePreLoadLibrary:
      WriteLn('Starting to load "', pdli.szDll, '" DLL');
    dliNotePreGetProcAddress:
      WriteLn('Want to get address of "', ImportName(pdli.dlp), '" in "', pdli.szDll, '" DLL');
    dliNoteEndProcessing:
      WriteLn('Ended the delaay load session for "', pdli.szDll, '" DLL');
    dliFailLoadLibrary:
      WriteLn('Failed to load "', pdli.szDll, '" DLL');
    dliFailGetProcAddress:
      WriteLn('Failed to get proc address for "', ImportName(pdli.dlp), '" in "', pdli.szDll, '" DLL');
  end;
 
  { Call the old hooks if they are not nil }
  { This is recommended to do in case the old hook do further processing }
  if dliNotify in [dliFailLoadLibrary, dliFailGetProcAddress] then
  begin
    if Assigned(LOldNotifyHook) then
      LOldFailureHook(dliNotify, pdli);
  end else
  begin
    if Assigned(LOldNotifyHook) then
      LOldNotifyHook(dliNotify, pdli);
  end;
 
  Result := nil;
end;
 
 
 
begin
  { Install new delayed loading hooks }
  LOldNotifyHook  := SetDliNotifyHook2(MyDelayedLoadHook);
  LOldFailureHook := SetDliFailureHook2(MyDelayedLoadHook);
 
  { Calling an existing delayed external routine }
  GetDesktopWindow;
 
  try
    { Calling an unexisting delayed external routine in an existing library }
    GetFooBar;
  except
  end;
 
  try
    { Calling an unexisting delayed external routine in an unexisting library }
    GetFooBarBar;
  except
  end;
 
  { Reset the hooks }
  SetDliNotifyHook2(LOldNotifyHook);
  SetDliFailureHook2(LOldFailureHook);
 
  Readln;
end.

Uses

  • SysInit.SetDliNotifyHook2
  • SysInit.SetDliFailureHook2
  • SysInit.TDelayedLoadHook
  • SysInit.dliNotification
  • SysInit.DelayLoadInfo
  • SysInit.TDelayLoadInfo
  • SysInit.PDelayLoadInfo
  • SysInit.DelayLoadProc
  • SysInit.TDelayLoadProc
  • SysInit.PDelayLoadProc

See Also

Personal tools
Previous Versions