?
Solved

Stupid Question (LoadLibrary)

Posted on 2010-09-17
9
Medium Priority
?
778 Views
Last Modified: 2012-05-10
Hello,

This a very stupid quesiton (maybe)... but, i prefer to ask! hehe

Example

TSomethingW = record
  FuncW: function (Something: PWideChar): Boolean; StdCall;
  hLib: THandle;
end;
PSomethingW = ^TSomethingW;

TSomethingA = record
  FuncA: function (Something: PAnsiChar): Boolean; StdCall;
  hLib: THandle;
end;
PSomethingA = ^TSomethingA;

var
  SomethingW: PSomethingW;
  SomethingA: PSomethingA;
begin
  New(SomethingW);
  FillChar(SomethingW^, SizeOf(TSomethingW), 0);
  //looking for unicode function, if supported
  SomethingW^.hLib := LoadLibrary(somedll.dll);
  if LongBool(SomethingW^.hLib) then
  begin
    SomethingW^.FuncW := GetProcAddress(SomethingW^.hLib, 'SomethingW');

    //now we check if there is unicode support for this DLL, if not, its ANSI only
    if SomethingW^.FuncW = nil then
    begin
      //its ANSI and supposed to have a "SomethingA" exported func to work with ansi
      //but, i need to FreeLibrary for SomethingW^ and LoadLibrary for SomethingA or i can simple
      New(SomethingA);
      FillChar(SomethingA^, SizeOf(TSomethingA), 0);
      SomethingA^.hInstance := SomethingW^.hInstance; //?!?!?!?!?
      Dispose(SomethingW); //freeing
  end;

i need to freelibrary for somethingW and loadlibrary for somethingA or i can just pass the Handle of loaded library to SomethingA?

Regards,
Carlos
0
Comment
Question by:cebasso
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 4
  • 3
  • 2
9 Comments
 
LVL 14

Expert Comment

by:systan
ID: 33703224
So thus the code has a problem for you?   I see your code is Ok.
but Im not sure  if you can pass the load from w to a with this code, and why are you doing this? for what reason?
SomethingA^.hInstance := SomethingW^.hInstance;
0
 
LVL 4

Author Comment

by:cebasso
ID: 33703278
Hello!
My program has a plugin framework... i have a struct/record for ANSI and WIDE(Unicode)

For old plugins, its ANSI and new plugins WIDE
For backward compatibility i need to support ANSI yet
So, with a new version of the engine, first i check if the plugin was upgraded to WIDE, if not, i use the old Struct (ANSI)
But, i load it from a StructW = WIDE, if there is no unicode support, then i load the old structA = ANSI... my doubt is, if i can just pass the loaded handle to the StructA^.hLib and use to call the plugin, or if i need to FreeLibrary at the StructW^.hLib and load for StructA^.hLib like my example above!
0
 
LVL 14

Expert Comment

by:systan
ID: 33703501
I guess you can't, Delphi doesn't support automatic type conversions betwwen Ansi and Wide string types.  Someone correct me if I'm wrong.
0
Independent Software Vendors: We Want Your Opinion

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 
LVL 4

Author Comment

by:cebasso
ID: 33703778
i think that you dont understood hehe
but no problem, i found a way!
i can't gave you the points, i'm sorry...
thank you anyway!
Cheers!
0
 
LVL 32

Accepted Solution

by:
Ephraim Wangoya earned 2000 total points
ID: 33703981
 No need to unload the library, just pass it on since it has both functions for unicode and ansi

  PSomethingW = ^TSomethingW;
  TSomethingW = record
    FuncW: function (Something: PWideChar): Boolean; StdCall;
    hLib: THandle;
  end;

  PSomethingA = ^TSomethingA;
  TSomethingA = record
    FuncA: function (Something: PAnsiChar): Boolean; StdCall;
    hLib: THandle;
  end;

function SupportsUnicode(AHandle: THandle; const AFunctionName: string): Boolean;
var
  FunctPointer: Pointer;
begin
  FuntionPointer := GetProcAddress(AHandle, AFunctionName);
  Result := FunctionPointer <> nil;
end;

procedure YourProcedure;
var
  LibraryHandle: THandle;
  SomethingW: PSomethingW;
  SomethingA: PSomethingA;
begin
  LibraryHandle := LoadLibrary('somedll.dll');
  if LibraryIsValid then
    try
      if SupportsUnicode(LibraryHandle, 'SomethingW') then
      begin
        New(SomethingW);
        FillChar(SomethingW^, SizeOf(TSomethingW), 0);
        SomethingW^.hLib := LibraryHandle;
        try
          SomethingW^.FuncW := GetProcAddress(SomethingW^.hLib, 'SomethingW');
          //do your work
        finally
          Dispose(SomethingW);
        end;
      end
      else
      begin
        New(SomethingA);
        FillChar(SomethingA^, SizeOf(TSomethingA), 0);
        SomethingA^.hLib := LibraryHandle;
        try
          SomethingA^.FuncA := GetProcAddress(SomethingW^.hLib, 'SomethingA');
          //do your work
        finally
          Dispose(SomethingA);
        end;
      end;
    finally
      FreeLibrary(LibraryHandle);
    end;
  end;
0
 
LVL 32

Expert Comment

by:Ephraim Wangoya
ID: 33704008
Answer is you don't need to unload the library, look at my last comment.
0
 
LVL 32

Expert Comment

by:Ephraim Wangoya
ID: 33704055
Sorry typo

function SupportsUnicode(AHandle: THandle; const AFunctionName: string): Boolean;
var
  FunctPointer: Pointer;
begin
  FunctPointer := GetProcAddress(AHandle, PChar(AFunctionName));
  Result := FunctPointer <> nil;
end;
0
 
LVL 4

Author Closing Comment

by:cebasso
ID: 33704166
Hey thanks!

But i still need a hLib var at the Struct since it will be added in a TList, so latelly i can know the instance of the plugin :D
But you answered my question, if its needed to unload in StructW first and re-load for StructA.

Cheers!
0
 
LVL 4

Author Comment

by:cebasso
ID: 33704181
@systan thank you too for starting to help me!

Best Regards!
0

Featured Post

[Webinar] How Hackers Steal Your Credentials

Do You Know How Hackers Steal Your Credentials? Join us and Skyport Systems to learn how hackers steal your credentials and why Active Directory must be secure to stop them.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

A lot of questions regard threads in Delphi.   One of the more specific questions is how to show progress of the thread.   Updating a progressbar from inside a thread is a mistake. A solution to this would be to send a synchronized message to the…
Creating an auto free TStringList The TStringList is a basic and frequently used object in Delphi. On many occasions, you may want to create a temporary list, process some items in the list and be done with the list. In such cases, you have to…
Michael from AdRem Software outlines event notifications and Automatic Corrective Actions in network monitoring. Automatic Corrective Actions are scripts, which can automatically run upon discovery of a certain undesirable condition in your network.…
Michael from AdRem Software explains how to view the most utilized and worst performing nodes in your network, by accessing the Top Charts view in NetCrunch network monitor (https://www.adremsoft.com/). Top Charts is a view in which you can set seve…
Suggested Courses

764 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question