News:

Masm32 SDK description, downloads and other helpful links
Message to All Guests
NB: Posting URL's See here: Posted URL Change

Main Menu

Problems attempting to make a static lib file

Started by Jason, November 06, 2024, 11:55:44 AM

Previous topic - Next topic

Jason

Hi Guys,

Very rusty here with ASM, so please bear with me.  :biggrin:

I'm encountering a problem attempting to make a static lib file and getting it to work in a MS Visual Studio C/C++ project.

Just doing a simple function at this stage to add two numbers.

.486
.model flat, stdcall
.code

start:

addnums proc num1:dword, num2:dword
    mov eax, num1
    mov ecx, num2
    add eax, ecx
    ret
addnums endp

end start

It seems to compile and link happily if I do the following and generates an 'addnums.lib' file.

ml.exe /c /coff addnums.asm
link /NOLOGO /SUBSYSTEM:CONSOLE /out:addnums.lib addnums.obj

But if I attempt to use the generated lib file in my C/C++ project it says "Warning LNK4003 - invalid library format; library ignored"

Any ideas on what I might be missing here would be greatly appreciated.  :thumbsup:






sinsi

I thought you would use LIB, not LINK?
VS might expect the procedure name to be "decorated" too.

Jason

Hi Sinsi, thanks for the reply.

I was just about to post, I got it 'recognised' by VS by using Polib and no longer get that error. However, I am now getting other errors.

Severity Code Description Project File Line Suppression State
Error LNK2001 unresolved external symbol _addnums
Error LNK1120 4 unresolved externals
Error LNK2001 unresolved external symbol __imp__system
Error LNK2001 unresolved external symbol ___CxxFrameHandler3
Error LNK2001 unresolved external symbol ___std_terminate

I suspect that the first one is due to the naming decorations that you just mentioned. How does one go about 'decorating' the names?

Many thanks, once again.

Jason

Scratch the above post, I've now got the error down to being unable to find the function

Error LNK2001 unresolved external symbol _addnums
Happening whether I do this "extern "C" double addnums(double a, double b)" or "extern "C" double _addnums(double a, double b)"


This is my main project as it stands now. The asm code is still the same as in the initial post.

#include <iostream>

#pragma comment(lib, "R:/Programming Archive/Source/asm/bin/addnums.lib")

extern "C" double addnums(double a, double b);
//double _addnums(double a, double b);

int main()
{
    std::cout << addnums(2,3);
    system("PAUSE");
}

sinsi

These two conflict
.model flat, stdcall

extern "C" double addnums(double a, double b)
The ASM code expects integers but the C code is for doubles...

No idea about C/C++ but if you get the calling convention right I assume that the linker would decorate the export name properly.

Jason

Ah, right you are! I mistakenly took DWORD as being a double, where it should be an int and have corrected that part of the code.

extern "C" int addnums(int a, int b);

int main()
{
    std::cout << addnums(2,3);
    system("PAUSE");
}


Still unfortunately having grief with the linker though.

Error LNK2001 unresolved external symbol _addnums
It's still insisting that it cant find _addnums (with an underscore).  :undecided:

Jason

Dumpbin.exe seems to show that the exported lib has the function in there happily.

    2 public symbols

        1 _addnums@8
        1 _start

sinsi

I know SFA about C/C++ but found this
extern "C" int __stdcall addnums(int x,int y)This also assumes you are building a 32-bit app.

That's about as far as I can go since the library seems correct :thumbsup:

Jason

Thanks Sinsi, I was just replying as your post popped up.


I got it going, but geez, I had to jump through some hoops with Visual Studio.

I had to do the following,

Configuration properties > Calling Convention > __stdcall (/Gz)
Configuration properties > Linker > Advanced > Image Has Safe Exception Handlers - No (/SAFESEH:NO)

Don't know if what I have done there is a bad thing or what?  :badgrin:


I guess if anything else, it gives me a playing field when I can test out what I'm trying to do. Can work out the finer details later on. Haha!

Many thanks for your assistance, Sinsi   :thumbsup:

sinsi

Can you do me a favour? Revert to the original configuration options and try that declaration?
I'm curious to see if that fixed it.

It seems to me that forcing an entire C program to use stdcall is...excessive :badgrin:

zedd151

"extern C" but not "addnums proc C, arg:dword, arg2:dword"
Is that legit?

Shouldn't the procedure be c as well? Looks weird, so I ask..

Btw, seems it would be way easier just to use a batch file. No interference from VS that way.  :tongue:  You can then write the command line arguments exactly as you need them, not as VS thinks they should be.

fearless

AddNums.asm:

.486
.model flat, stdcall
.code

include AddNums.inc

;------------------------------------------------------------------------------
; Add two integers together and returns the result
;------------------------------------------------------------------------------
AddIntegers PROC Num1:DWORD, Num2:DWORD
    mov eax, Num1
    add eax, Num2
    ret
AddIntegers ENDP


END

No need to add END start, just add END for your library in the main file. You can also include other files, other .asm modules or .inc files to help with organizing everything.

AddNums.inc:

;==============================================================================
;
; AddNums Library
;
;==============================================================================

AddIntegers PROTO Num1:DWORD, Num2:DWORD

The AddNums.inc is an include file for assembler users.

For c/cpp users you can create an header file for them:

AddNums.h:

/*=============================================================================

 AddNums Library

=============================================================================*/

#ifdef __cplusplus
extern "C" {
#endif

#ifdef _MSC_VER    // MSVC compiler
#define APIEXPORT __declspec(dllexport) __stdcall
#else
#define APIEXPORT
#endif

int APIEXPORT AddIntegers(int Num1, int Num2);

#ifdef __cplusplus
}
#endif

You can then copy the AddNums.lib and AddNums.h to your visual studio solution to compile the test console program:


AddNumbers.cpp:

#include <iostream>

#include <AddNums.h>
#pragma comment(lib, "AddNums.lib")

int main()
{
    std::cout << AddIntegers(2, 3) << std::endl;
    system("PAUSE");
}

I added AddNums.h to the header files section in the solution. Other settings I modified in the test program (AddNumbers.exe) in the visual studio solution are for Release (x86) Win32:

Advanced->Character Set: Not Set
Advanced->Whole Program Optimization: No Whole Program Optimization
VC++ Directories->Include Directories: <Add this projects folder to this so that it will pick up the AddNums.h that you copied here.>
C/C++->General->Debug Information Format: None
C/C++->Code Generation->Enable C++ Exceptions: No
C/C++->Code Generation->Runtime Library: Multi-threaded (/MT)
C/C++->Code Generation->Security Check: Disable Security Check (/GS-)
Linker->Debugging->Generate Debug Info: No
Linker->Advanced->Randomized Base Address: No (/DYNAMICBASE:NO)
Linker->Image Has Safe Exception Handlers: No (/SAFESEH:NO)




Jason

Wowza. Heaps of replies in here now. Many thanks, everyone.

@fearless - Yeah, I ended up removing the references to 'start'. Dumpbin, bought that to my attention when it was showing up as an exported function.

Lots of suggestions here for my to try out though. I haven't attempted to mix Asm generated libs with a C/C++ project before, so I'm certainly open to any suggestions.  :biggrin:

NoCforMe

Quote from: zedd151 on November 06, 2024, 02:29:49 PMBtw, seems it would be way easier just to use a batch file. No interference from VS that way. 

Yabbut, it looks like they're using Visual Studio because they have a C/C++ project they want to link it to. So using a batch file probably isn't an option.
Assembly language programming should be fun. That's why I do it.

zedd151

Quote from: NoCforMe on November 06, 2024, 03:25:11 PMYabbut, it looks like they're using Visual Studio because they have a C/C++ project they want to link it to. So using a batch file probably isn't an option.
I somehow missed that part, thanks.