News:

MASM32 SDK Description, downloads and other helpful links
MASM32.com New Forum Link
masmforum WebSite

prototypes in DLL's when calling implicitly

Started by allynm, October 17, 2009, 06:17:13 PM

Previous topic - Next topic

allynm

Hi everyone -

I am trying to invoke a proc in a DLL--just a simple MessageBox as a test.  I'm trying to implicitly load the DLL with a includelib statement at the beginning of the calling module.  The .lib file lwith the exports ooks OK when I dump it with objconv or with dumpbin. The .obj file from the caller seems to link successfully with the .lib file.  However, when I run the executable, no message box pops open.  Do I need to have a proto in the original DLL file for the messagebox proc that gets called, or maybe someplace else?  At the moment, there is no include file in either the DLL or the caller.  Got a feeling that is where the problem is arising.

...yet another in a series of novice questions.

Thanks,
Mark Allyn


Vortex

Hi Mark,

Here is a quick example.

Code of the DLL :


.386
.model flat, stdcall
option casemap :none

include     \masm32\include\windows.inc
include     \masm32\include\user32.inc

includelib  \masm32\lib\user32.lib

.code

LibMain     PROC instance:DWORD,reason:DWORD,unused:DWORD

    mov     eax,1
    ret

LibMain     ENDP

MsgBox      PROC szText:DWORD,szCaption:DWORD

    invoke  MessageBox,0,szText,szCaption,MB_OK
    ret

MsgBox      ENDP

END         LibMain


The application calling the function MsgBox :


.386
.model flat, stdcall
option casemap :none

include     \masm32\include\windows.inc
include     \masm32\include\kernel32.inc

includelib  \masm32\lib\kernel32.lib

includelib  Test.lib

MsgBox      PROTO :DWORD,:DWORD

.data

Text        db 'Message box test',0
Caption     db 'Hello',0

.code

start:

    invoke  MsgBox,ADDR Text,ADDR Caption
    invoke  ExitProcess,0

END start

allynm

Hi Vortex:

Thanks for putting me straight on this.  I really had a fundamental misunderstanding of what you coded and assembled as Test.lib.  I was under the misapprehension that some kind of "import library" needed to be constructed.  So, I followed Iczelion's tute on how to create an import library.  I built a .lib file out of LibMain pretty nearly exactly as you did.  You can probably anticipate where I am going with this....anyway, I merrily constructed an "import lib" out of my original dll following Icz's direction.  It was this version of what you are calling Test.lib that I used in the includelib statement, not the original .lib.  I'm probably confusing you, but hopefully not.  All of this reveals a fundamental ignorance I have of what import libraries are.  Oddly, thanks to Iczelion, I know how to build them but I have no idea what to do with them...

So what gives with this import lib stuff?  Why might I need one  If you or someone would enlighten me I would greatly appreciate.

Regards,
Mark

Vortex

Hi Mark,

When you build a DLL, the linker will create automatically an import library. You don't need to use any other tools to create an import library while assembling and linking the DLL code. The import library informs the linker about the assocation of external functions with DLLs. Here is where you can find more explanation about import libraries :

http://www.masm32.com/board/index.php?topic=12432.msg95414#msg95414

If you download and rebuild the example project I posted, you will see that it's the second line below in the batch file creating both the DLL and the import library :


\masm32\bin\ml /c /coff Test.asm
\masm32\bin\polink /SUBSYSTEM:WINDOWS /DLL /DEF:Test.def Test.obj

\masm32\bin\ml /c /coff Demo.asm
\masm32\bin\polink /SUBSYSTEM:WINDOWS Demo.obj


Test.lib is required to tell the linker that the MsgBox function is exported by Test.dll

allynm

Hi Vortex -

Thanks for the link.  I followed it and picked up an improved understanding.

There is more to this DLL story than I appreciated.  I had been putting a .data section with some strings in it in the DLL source file.  I still couldn't get the call to the DLL to function and pop the Mbox when the strings were in the DLL.  HOWEVER, if you pass the strings in the calling program the way you did it, then my DLL works fine.  So, I learned something significant that makes the implicit call different, it appears, from the explicit call.  Because, if you call the MBox by loading it explicitly then the MBOX pops open as it should EVEN WHEN the strings are in the .data section of the DLL.  I don't understand why it should work this way, but it does.  And it's confusing as all get out.

I have no doubt but what you and the other experts know exactly why this would be true.

Regards,
Mark