[OT?] Borlands Tasm32 syntax for calling a function in a specific DLL.

16 views
Skip to first unread message

R.Wieser

unread,
Jul 19, 2022, 11:49:07 AM7/19/22
to
Hello all,

I'm using Borlands Tasm32 (v5.0) and just ran into a situation where I had
to call 'DllGetVersion' inside ComCtl32. The problem is that that function
exists in several other DLLs (shell32 to name another).

IOW, although I can write 'call DllGetVersion, ...' I never know which DLL
will actually get called.

My question:

Does anyone here know if Tasm32 knows an assemble-time syntax to call a
function from a specific DLL ? (would be handy for a few other functions
too)

Remarks:

I currently used the runtime "LoadLibary", "GetProcAddress" solution, but
thats cumbersome.

I could also rename the function itself (from "DllGetVersion" to something
like "ComCtl32_GetVersion") and rebuild the libarary, but thats a ... well,
not a solution I'd really like either.

Regards,
Rudy Wieser

P.s.
Anyone knows where I can find ComCtl32 v6.x ?


Frank Kotler

unread,
Jul 19, 2022, 10:04:40 PM7/19/22
to
On 07/19/2022 11:36 AM, R.Wieser wrote:
> Hello all,
>
Hi Rudy,
Seems on-topic to me.

Best,
Frank

George Neuner

unread,
Jul 21, 2022, 8:21:38 AM7/21/22
to
On Tue, 19 Jul 2022 17:36:23 +0200, "R.Wieser"
<add...@nospicedham.not.available> wrote:

>I'm using Borlands Tasm32 (v5.0) and just ran into a situation where I had
>to call 'DllGetVersion' inside ComCtl32. The problem is that that function
>exists in several other DLLs (shell32 to name another).
> :
>Does anyone here know if Tasm32 knows an assemble-time syntax to call a
>function from a specific DLL ? (would be handy for a few other functions
>too)
> :
>I currently used the runtime "LoadLibary", "GetProcAddress" solution, but
>thats cumbersome.

Sorry, I never used Tasm (any version), but WRT to GetProcAddress I
don't believe there is any other way to guarantee you will get the
right function.

One suggestion though:

If you know the DLL is already resident - because you static linked or
already have loaded it dynamically - you should use GetModuleHandle
instead of LoadLibrary. Calls to LoadLibrary must be paired with
calls to FreeLibrary because they maintain usage reference counts on
the loaded module. If you don't pair them properly, modules can end up
either prematurely unloaded or locked into memory.

> :
>Regards,
>Rudy Wieser
>
>P.s.
>Anyone knows where I can find ComCtl32 v6.x ?

https://www.dll-files.com/comctl32.dll.html
Look near the bottom of the page for 6.x

Hope this helps.
George

R.Wieser

unread,
Jul 21, 2022, 9:52:00 AM7/21/22
to
George,

> Sorry, I never used Tasm (any version), but WRT to GetProcAddress
> I don't believe there is any other way to guarantee you will get
> the right function.

There is, and I mentioned it just below the 'GetProcAddress' method.

> If you know the DLL is already resident you should use GetModuleHandle
> instead of LoadLibrary.

Does it make a difference ? (whats the 'should' about ?)

Regards,
Rudy Wieser


George Neuner

unread,
Jul 21, 2022, 2:19:15 PM7/21/22
to
On Thu, 21 Jul 2022 15:43:03 +0200, "R.Wieser"
<add...@nospicedham.not.available> wrote:

>George,
>
>> Sorry, I never used Tasm (any version), but WRT to GetProcAddress
>> I don't believe there is any other way to guarantee you will get
>> the right function.
>
>There is, and I mentioned it just below the 'GetProcAddress' method.

Yes, but it involved recompiling the module. Most people are not in a
position to rebuild system DLLs, so that isn't a general solution.


>> If you know the DLL is already resident you should use GetModuleHandle
>> instead of LoadLibrary.
>
>Does it make a difference ? (whats the 'should' about ?)

'should' means it is the best choice ... at least under the given
circumstances.


And it does make a difference, which I explained previously and will
expound on now:


LoadLibrary manipulates reference counts on the loaded module and
every call to LoadLibrary has to be paired with a call to FreeLibrary.
Unbalanced calls to LoadLibrary can cause a shared DLL to end up
locked into memory.
[Note that application exit automatically calls FreeLibrary for all
DLLs attached to the process. So application exit will balance one
LoadLibrary call for any given library.]

GetModuleHandle just searches for an already loaded module and returns
a handle to it (that can be passed to GetProcAddress).


If you are dealing with an already loaded DLL (for which you don't
have a handle available), you have to do one of the following:
(in C)

hnd = GetModuleHandle( "ComCtl32" );
ptr = GetProcAddress( hnd, "DllGetVersion" );

or

hnd = LoadLibrary( "ComCtl32" );
ptr = GetProcAddress( hnd, "DllGetVersion" );
FreeLibrary( hnd );

Whenever you call LoadLibrary, you also have to call FreeLibrary
UNLESS you are deliberately loading a /new/ DLL and intend it to
remain resident until application exit. And if you do deliberately
load something, you 'should' (best practice) save the returned handle
because it is simpler than having to discover it again later.


I realize the documentation[1,2] says application exit frees libraries
regardless of reference counts ... but "free" in this case means
"detached from your process" and it does not necessarily mean the
library can or will be be unloaded from memory. In particular, if the
library instantiates one or more COM objects based on LoadLibrary
calls (which in general you can't know), and those loads are not
balanced by FreeLibrary calls, the library will never be unloaded (ie.
it will be locked into memory).

NB: DLLs in Windows can have their own private heaps not associated
with any client process. Objects created on a private heap on behalf
of a client process might be able to survive the termination of that
process. COM objects have their own reference counts which are
unrelated to reference counts on the module that implements them.
Windows will not unload any module that still has live COM objects.

To be safe you need to make sure you always balance explicit
LoadLibrary calls with FreeLibrary calls.


>Regards,
>Rudy Wieser

Hope this helps.
George

[1]
https://docs.microsoft.com/en-us/windows/win32/api/libloaderapi/nf-libloaderapi-loadlibrarya
[2]
https://docs.microsoft.com/en-us/windows/win32/api/libloaderapi/nf-libloaderapi-freelibrary

R.Wieser

unread,
Jul 22, 2022, 5:11:46 AM7/22/22
to
George,

>>> I don't believe there is any other way to guarantee you will get
>>> the right function.
>>
>>There is, and I mentioned it just below the 'GetProcAddress' method.
>
> Yes, but it involved recompiling the module.

So there /is/ a way, but you do not like it. Thats something quite
different.

> Most people are not in a position to rebuild system DLLs,

Whut ? Who has said anything about rebuilding *DLLs* ? (library, not DLL)

> so that isn't a general solution.

I can't remember having said anything about it needing to work for everyone
else too ...

But yes, that is why I posted "not a solution I'd really like either" -
*even though* I wager to guess that I'm the only one here who uses Borlands
Tasm32 v5.x ....

Regards,
Rudy Wieser


Reply all
Reply to author
Forward
0 new messages