dcsimg
CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 5 of 5

Thread: I'm getting a linking error while linking to my simple DLL library.

  1. #1
    Join Date
    Jul 2017
    Posts
    48

    I'm getting a linking error while linking to my simple DLL library.

    Probably I haven't understand correctly how to export a dll and this is why I'm getting this linking error. Because I really don't know what is happening I'm going to post all of my code (don't worry it's short).

    This is happening only if i compile the client code as cpp code. If I tell visual studio to compile the client code as c code (notice that I compiled the DLL code as c code) then i don't get any linking errors. Why is this happening? I want my library to be able to get linked in both c or c++ code for portability.

    DLL Source Code Header File:
    Code:
    #ifndef CSocket_Imp_H
    #define CSocket_Imp_H
    
    
    //Define for DLL EXPORT.
    #ifndef DLL_CSocket_IMPORT
    	#define DLL_CSocket_MACRO __declspec(dllexport)
    
    
    //Define for DLL IMPORT.
    #else
    	#define DLL_CSocket_MACRO __declspec(dllimport)
    #endif
    
    
    //-_-_-_-_-_CSocket Structure-_-_-_-_-_//
    typedef struct CSocket_Socket
    {
    	unsigned short family;
    	unsigned short   port;
    	unsigned long address;
    	char     is_listening;
    
    }CSocket_Socket;
    //-_-_-_-_-_CSocket Structure-_-_-_-_-_//
    
    
    
    //Initialize CSocket.
    DLL_CSocket_MACRO const char * CSocket_Init();
    
    
    //Create a CSocket Socket Object.
    DLL_CSocket_MACRO CSocket_Socket *CSocket_Create();
    
    //Bind a Socket.
    DLL_CSocket_MACRO int CSocket_Bind(CSocket_Socket *sock, const char *ip, short port);
    
    //Make a Binded socket a Listen Socket.
    DLL_CSocket_MACRO int CSocket_Listen(CSocket_Socket *sock, int queue_length);
    
    //Accept Connections.
    DLL_CSocket_MACRO CSocket_Socket * CSocket_Accept(CSocket_Socket *sock);
    
    //Connect to another socket.
    DLL_CSocket_MACRO int CSocket_Connect(CSocket_Socket *sock, const char *ip, short port);
    
    //Receive data from a socket.
    DLL_CSocket_MACRO int CSocket_Recv(CSocket_Socket *sock, char *data_in, int size);
    
    //Send data through a socket.
    DLL_CSocket_MACRO int CSocket_Send(CSocket_Socket *sock, char *data_out, int size);
    
    //Close a socket.
    DLL_CSocket_MACRO int CSocket_Close(CSocket_Socket *sock);
    
    #endif

    DLL Source Code C File:
    Code:
    #include "CSocket_Imp.h"
    #include <stdio.h>
    #include <stdlib.h>
    
    #ifdef _WIN32
    
    #include <WinSock2.h>
    
    #endif
    
    
    
    //Initialize CSocket.
    const char * CSocket_Init()
    {
    
    	//---------------------------Windows Implementation---------------------------//
    	#ifdef _WIN32
    	WSADATA data;
    
    	//Start Up the Windows Socket Api.
    	int status = WSAStartup(MAKEWORD(2, 2), &data);
    
    	//Something Went Wrong.
    	if (status != 0)
    	{
    
    		//The network system is not ready.
    		if (status == WSASYSNOTREADY)
    			return "The underlying network subsystem is not ready for network communication";
    
    		//Unsupported Version.
    		else if (status == WSAVERNOTSUPPORTED)
    			return "The version of Windows Sockets support requested is not provided by this particular Windows Sockets implementation.";
    
    
    		//Blocking Operation.
    		else if (status == WSAEINPROGRESS)
    			return "A blocking Windows Sockets 1.1 operation is in progress.";
    
    
    		//Limit.
    		else if (status == WSAEPROCLIM)
    			return "A limit on the number of tasks supported by the Windows Sockets implementation has been reached.";
    
    		//WSADATA invalid pointer.
    		else if (status == WSAEFAULT)
    			return "The lpWSAData parameter is not a valid pointer.";
    	}
    
    	//Everything is fine.
    	return "";
    	//---------------------------Windows Implementation---------------------------//
    
    
    
    	//----------------------------Linux Implementation----------------------------//
    	#else
    	return "";
    	//----------------------------Linux Implementation----------------------------//
    
    	#endif
    }
    
    
    
    //Create a CSocket Socket Object.
    CSocket_Socket * CSocket_Create()
    {
    	return NULL;
    }
    
    
    
    //Bind a Socket.
    int CSocket_Bind(CSocket_Socket * sock, const char * ip, short port)
    {
    	return 0;
    }
    
    
    
    //Make a Binded socket a Listen Socket.
    int CSocket_Listen(CSocket_Socket * sock, int queue_length)
    {
    	return 0;
    }
    
    
    
    //Accept Connections.
    CSocket_Socket * CSocket_Accept(CSocket_Socket * sock)
    {
    	return NULL;
    }
    
    
    
    //Connect to another socket.
    int CSocket_Connect(CSocket_Socket * sock, const char * ip, short port)
    {
    	return 0;
    }
    
    
    
    //Receive data from a socket.
    int CSocket_Recv(CSocket_Socket * sock, char * data_in, int size)
    {
    	return 0;
    }
    
    
    
    //Send data through a socket.
    int CSocket_Send(CSocket_Socket * sock, char * data_out, int size)
    {
    	return 0;
    }
    
    
    
    //Close a socket.
    int CSocket_Close(CSocket_Socket * sock)
    {
    	return 0;
    }


    Header File To Be Included By The Client:
    Code:
    #ifndef CSocket_H
    #define CSocket_H
    
    //Define this header as DLL Import.
    #define DLL_CSocket_IMPORT
    
    //Include the Csocket Implementantion.
    #include "CSocket_Imp.h"
    
    #endif


    Client Source Code:
    Code:
    #include "CSocket.h"
    
    int main()
    {
    
    	CSocket_Init();
    	return 0;
    }
    But i'm getting this link error:
    Code:
    1>Source.obj : error LNK2019: unresolved external symbol "__declspec(dllimport) char const * __cdecl CSocket_Init(void)" (__imp_?CSocket_Init@@YAPBDXZ) referenced in function _main
    1>C:\Users\zervos\source\repos\csocket_solution\Debug\Test.exe : fatal error LNK1120: 1 unresolved externals
    Last edited by babaliaris; October 28th, 2018 at 11:13 PM.

  2. #2
    2kaud's Avatar
    2kaud is offline Super Moderator Power Poster
    Join Date
    Dec 2012
    Location
    England
    Posts
    6,487

    Re: I'm getting a linking error while linking to my simple DLL library.

    You're come across the fabled c++ 'mangled name' link issue. When programming in c, the link name is just the function name. However for c++ the link name also includes type info as well for each parameter (known as the mangled name!). Hence the linker tries to match the c++ mangled name with the ordinary c name and doesn't get a match so reports an error.

    The way round this is for c++ import code to specify that the external name is for c and not for c++. This is done using extern "C" for the imports. Note CAPITAL C - not lowercase c!

    See https://docs.microsoft.com/en-us/cpp...p?view=vs-2017 for details (3rd meaning in the list) and an example of usage.
    All advice is offered in good faith only. All my code is tested (unless stated explicitly otherwise) with the latest version of Microsoft Visual Studio (using the supported features of the latest standard) and is offered as examples only - not as production quality. I cannot offer advice regarding any other c/c++ compiler/IDE or incompatibilities with VS. You are ultimately responsible for the effects of your programs and the integrity of the machines they run on. Anything I post, code snippets, advice, etc is licensed as Public Domain https://creativecommons.org/publicdomain/zero/1.0/ and can be used without reference or acknowledgement. Also note that I only provide advice and guidance via the forums - and not via private messages!

    C++17 Compiler: Microsoft VS2017 (15.8.9)

  3. #3
    Join Date
    Jul 2017
    Posts
    48

    Talking Re: I'm getting a linking error while linking to my simple DLL library.

    I changed my macros like this:

    Code:
    //Define for DLL EXPORT.
    #ifndef DLL_CSocket_IMPORT
    	#define DLL_CSocket_MACRO __declspec(dllexport)
    	#define EXTERN 
    	#define EXTERN_STRING 
    
    
    //Define for DLL IMPORT.
    #else
    	#define DLL_CSocket_MACRO
    	#define EXTERN extern
    	#define EXTERN_STRING "C"
    #endif
    
    DLL_CSocket_MACRO  EXTERN EXTERN_STRING type function_name();
    It works!

    But is there a way to know if this header file is included in a c or cpp file? Because my macros as they are now if i try to link this library in a c file i will have problems with this:
    Code:
    //Define for DLL IMPORT.
    #else
    	#define DLL_CSocket_MACRO
    	#define EXTERN extern
    	#define EXTERN_STRING "C"
    #endif
    C doesn't know the extern "C" keyword so I want to do something like this:
    Code:
    //Define for DLL IMPORT.
    #else
    
            //C++
            #ifdef CPP
    	    #define DLL_CSocket_MACRO
    	    #define EXTERN extern
    	    #define EXTERN_STRING "C"
    
            //C
            #else
                #define DLL_CSocket_MACRO __declspec(dllimport)
                #define EXTERN 
                #define EXTERN_STRING 
            #endif
    #endif
    I know that I can say the user to define CPP manually before including the header file of my library, but is there a way to automate this?

    Thank you
    Last edited by babaliaris; October 29th, 2018 at 12:08 PM.

  4. #4
    2kaud's Avatar
    2kaud is offline Super Moderator Power Poster
    Join Date
    Dec 2012
    Location
    England
    Posts
    6,487

    Re: I'm getting a linking error while linking to my simple DLL library.

    Yes there is. There is a pre-defined macro __cplusplus which is defined for a c++ compilation and not defined for a c compilation.

    See https://msdn.microsoft.com/en-us/library/b0084kay.aspx
    All advice is offered in good faith only. All my code is tested (unless stated explicitly otherwise) with the latest version of Microsoft Visual Studio (using the supported features of the latest standard) and is offered as examples only - not as production quality. I cannot offer advice regarding any other c/c++ compiler/IDE or incompatibilities with VS. You are ultimately responsible for the effects of your programs and the integrity of the machines they run on. Anything I post, code snippets, advice, etc is licensed as Public Domain https://creativecommons.org/publicdomain/zero/1.0/ and can be used without reference or acknowledgement. Also note that I only provide advice and guidance via the forums - and not via private messages!

    C++17 Compiler: Microsoft VS2017 (15.8.9)

  5. #5
    Join Date
    Jul 2017
    Posts
    48

    Re: I'm getting a linking error while linking to my simple DLL library.

    Quote Originally Posted by 2kaud View Post
    Yes there is. There is a pre-defined macro __cplusplus which is defined for a c++ compilation and not defined for a c compilation.

    See https://msdn.microsoft.com/en-us/library/b0084kay.aspx
    Thank you!!!

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  


Windows Mobile Development Center


Click Here to Expand Forum to Full Width




On-Demand Webinars (sponsored)