ClusterFonk
ClusterFonk

Reputation: 49

Library call failed c++ dll

vim docs state that I've got to use C calling conventions for all my functions. This in mind I wrote a bare minimum dll just to see if everything is ok.

#include <string>

std::string _declspec(dllexport) Meow() {
    std::string Meow = "Meow!";
    return Meow;
}

For compiling I wrote a makefile

test.dll: test.cpp
cl /LD test.cpp
clean: 
    del *.obj
    del *.dll
    del *.exp
    del *.lib

Compiled without any issues and copied the dll into my vim directory. In my understanding calling the function via

:call libcall("test.dll","Meow",0)<cr>

should work. But I keep getting Error 364: Library call failed for "Meow()". Changing the .dll name inside libcall to something that doesnt exist results in the same error, thus I came to the conclusion something is wrong with my dll. But then again my dll is compiled without any problems, which leaves me puzzled.

Upvotes: 0

Views: 264

Answers (2)

Luca Cappa
Luca Cappa

Reputation: 1999

The following should fix your example:

extern "C"
{  
    static char null_terminated_string[2048];
    char* _declspec(dllexport) Meow(char *arg) 
    {
        strncpy(null_terminated_string, arg, std::min(sizeof(null_terminated_string), strlen(arg));
        return null_terminated_string;
    }
}

Upvotes: 0

user7860670
user7860670

Reputation: 37587

I see at least two problems with your code:

  • In C++ names typically get mangled when exported so your Meow function will become something like ?Meow@@YA?AV?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@XZ.
  • Vim docs seem to state that function called with libcall must match some rather restrictive conditions:

The function must take exactly one parameter, either a character pointer or a long integer, and must return a character pointer or NULL. The character pointer returned must point to memory that will remain valid after the function has returned (e.g. in static data in the DLL).

Upvotes: 2

Related Questions