3

Is it possible to mimic the loadlibrary function? I want to load a library from a BLOB field without first writing it to a temporary file, and I need a solution which is not dependent on specific version of delphi compiler or windows, and does not trigger antivirus software.

3
  • 2
    "and does not trigger antivirus software" -- sadly, some antivirus software actually has had warnings about programs written in Delphi, with only "written in Delphi" being the suspicious part. Commented Aug 29, 2012 at 6:25
  • This is officially unsupported. There are hacks available but they really are hacks. Commented Aug 29, 2012 at 7:53
  • The accepted way to do encryption is to put the algo code in your app, but protect the key. It looks like you are trying to protect the algo as well. I don't believe that's any stronger than protecting just the key. Once you load it into memory anyway, you have no protection. The hackers can read your memory. You need the key to remain on the secure device. Commented Aug 29, 2012 at 22:02

3 Answers 3

7

Yes you can, and you need not loadlibrary to execute a code from memory - you need to allocate a memory using VirtualAlloc function with PAGE_EXECUTE flag set


Update: here is a quick and dirty demo of the code executed from memory for 32-bit Delphi - I only tested that it works:

type
  TIncMe = procedure(var I: Integer);

var
  IncMeProc: TIncMe;

procedure IncMe(var I: Integer);
begin
  Inc(I);
end;

procedure CopyIncMe;
var
  Size: LongWord;
  Tmp: Pointer;

begin
  Size:= LongWord(@CopyIncMe) - LongWord(@IncMe);
  Tmp:= VirtualAlloc(nil, Size, MEM_COMMIT or MEM_RESERVE, PAGE_EXECUTE_READWRITE);
  Move(Pointer(@IncMe)^, Tmp^, Size);
  IncMeProc:= Tmp;
end;

procedure TForm1.Button1Click(Sender: TObject);
var
  J: Integer;

begin
  J:= 0;
  CopyIncMe;
  while J < 10 do begin
    IncMeProc(J);
    ShowMessage(IntToStr(J));
  end;
  VirtualFree(@IncMeProc, 0, MEM_RELEASE);
end;
Sign up to request clarification or add additional context in comments.

7 Comments

Can you provide me with a working code, either in C++ or Delphi please?
If it's a dll you need to do more
I guess I can work with that. I have a decryption function which reads the BLOB field from the DB, writes it to a temporary file and then loads it with loadlibrary. With the above code, I can store my encryption function in a smart card, and load it directly to the memory.
If the stored code needs to call any external functions, there will be problems since the code won't know the relative offsets of those functions' addresses. Fixing up addresses is one of the tasks LoadLibrary performs.
+1 yes, you should be careful not to address external code; a function with local variables only is the best candidate to be moved to memory.
|
5

dzlib contains a ready made object for reading a dll from a resource into memory and using it without ever saving it to disc:

This is the main file ...

http://sourceforge.net/p/dzlib/code/147/tree/dzlib/trunk/src/u_dzResourceDllLoader.pas

.. but it needs other files from the same repository.

2 Comments

I wrote a quick mock up application with it and it worked... This weekend I'm gonna try and load some complex DLLs with initialization/finalization code and check them on a few Windows versions I know my customers are using. But it seems this library does the trick. Vielen Dank :-)
But always be aware that this is officially unsupported by MS. It's a hack and expect it to come back and bite you in the future.
4

There's an article on delphi.about.com, that shows how to load a dll from a resource.

It first loads the resource into memory, and then loads the dll from the resource using Memory Module

Instead of a resource, you can use a database or whatever source you want to load the dll from. Once it is in a memory stream, you can use the following code to load and execute the dll functions, which looks very much like 'normal' code to invoke a dll:

var
  btMM: PBTMemoryModule;
begin
  btMM := BTMemoryLoadLibary(mp_DllData, m_DllDataSize);
  try
    if btMM = nil then Abort;
    @m_TestCallstd := BTMemoryGetProcAddress(btMM, 'TestCallstd');
    if @m_TestCallstd = nil then Abort;
    m_TestCallstd('This is a Dll Memory call!');
  except
    Showmessage('An error occoured while loading the dll: ' + BTMemoryGetLastError);
  end;
  if Assigned(btMM) then BTMemoryFreeLibrary(btMM);
end;

1 Comment

I downloaded the demo on [link]nodeload.github.com/jasonpenny/democode/zipball/master[/link], but it fails on line 461 in BTMemoryModule.pas: l_successfull := l_DllEntry(Cardinal(l_code), DLL_PROCESS_ATTACH, nil); with an access violation. I believe the code is specific to a compiler version and/or windows version.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.