Generic function for loading a function from a DLL library I am trying to write a generic function for loading a function from a DLL library. I am in no way an expert on DLLs, that is why I ask.

We have discussed it first in my Stack Overflow question to discover the most obvious errors, and there were some crucial ones.



Current version of my code follows:

function LoadFunctionFromLibrary(const LibraryName, FunctionName: string; out FunctionPointer: Pointer): Boolean;

var
  LibraryHandle: THandle;

begin
  Result := False;
  FunctionPointer := nil;

  LibraryHandle := Winapi.Windows.LoadLibrary(PChar(LibraryName));
  if LibraryHandle = 0 then Exit;

  FunctionPointer := Winapi.Windows.GetProcAddress(LibraryHandle, PChar(FunctionName));

  if Assigned(FunctionPointer) then
    Result := True;
end;




This version of the function has been successfully tested on my EnableInput function:

function EnableInput(const Enable: Boolean): Boolean;

var
  BlockInput: function(Block: BOOL): BOOL; stdcall;

begin
  Result := LoadFunctionFromLibrary('User32.dll', 'BlockInput', @BlockInput) and
            BlockInput(not Enable);
end;
Just like Dangph, I wonder why you need this. There are other better approaches suggested in the previous comments.

Even if this is useful, Your solution is not great: 
 1. You repeatedly load the library and the function.
 2. There is no way for you to free the loaded libraries.

Here is a better way to do it:

type
  TFunctionLoader = class
  private
    FLibraries: TStrings;   // This stores the library handles and names
    FFunctions: TStrings;   // This stores the function pointers and names
  public
    constructor Create;
    destructor Destroy; override;
    function LoadFunction(const LibraryName, FunctionName: string; 
                          out FunctionPointer: Pointer): Boolean;
  end;

{ TFunctionLoader }

constructor TFunctionLoader.Create;
begin
  FLibraries := TStringList.Create;
  FFunctions := TStringList.Create;
end;

destructor TFunctionLoader.Destroy;
var
  i: Integer;
begin
  for i := 0 to FLibraries.Count - 1 do     // free all opened libraries
    Windows.FreeLibrary(THandle(FLibraries.Objects[i]));
  FLibraries.Free;                          // free other objects
  FFunctions.Free;
end;

function TFunctionLoader.LoadFunction(const LibraryName, FunctionName: string;
  out FunctionPointer: Pointer): Boolean;
var
  i: Integer;
  LibraryHandle: THandle;
begin
  i := FFunctions.IndexOf(FunctionName);    // Is the function already loaded?
  if i &gt;= 0 then
  begin                                     // Yes, just return the stored pointer
    FunctionPointer := Pointer(FFunctions.Objects[i]);
    Exit(True);
  end;

  i := FLibraries.IndexOf(LibraryName);     // No, test if the library is already loaded
  if i &lt; 0 then
  begin                                     // No, load it and store in FLibraries
    LibraryHandle := Windows.LoadLibrary(PChar(LibraryName));
    if LibraryHandle = 0 then Exit(False);  // Failed, quit
    i := FLibraries.AddObject(LibraryName, TObject(LibraryHandle));
  end;

  // Load the function from the library
  FunctionPointer := Windows.GetProcAddress(THandle(FLibraries.Objects[i]),
                                            PChar(FunctionName));
  Result := Assigned(FunctionPointer);      // succeeded?
  if Result then                            // Add the function to FFunctions
    FFunctions.AddObject(FunctionName, TObject(FunctionPointer));
end;


With above you can define var FunctionLoader: TFunctionLoader; somewhere and add this to the end of the unit

initialization
  FunctionLoader := TFunctionLoader.Create;
finalization
  FunctionLoader.Free;
end.


Use it as

Result := FunctionLoader.LoadFunction('User32.dll', 'BlockInput', @BlockInput)
          and BlockInput(not Enable);


All functions and libraries will be loaded only once and will be automatically freed.