I haven't found a solution to my problem, because of limited knowledge about dll Libraries.
I am using Matlab (R2017a) to integrate communication to a device through a dll, which is provided by the manufacturer (files - Xemo-DLL (64Bit) mit Header-Dateien (2.40)).
As far as I understand there is precompiled .dll in C and a header File in C++, beside a VB and VB.NET wrapper.
Question is: What is the best way to integrate the dll into Matlab?
A) I tried loadlibrary(XemoDll). It throws a lot of errors, iostream wasn't found. So I added extern "C" {} to the whole file, which created new errors at every function definition. Where do I have to insert it?
B) I tried to add NET.addAssembly(path\XemoDll.vb) of the VB.NET library. There is a Module with all wrapper functions. Matlabs gives the error "assembly manifest missing" Source: mscorlib.
I found a Tutorial on loading Dlls with the LoadLibrary() command from windows.h, and got it working.
I use a a DllInterface_mex function that gets the function name and calls the approriate function in the Dll.
Related
I made changes to a function in a COM DLL. I've been unable to figure out how to debug the changes I made.
Background:
I recently inherited a Visual Studio 2012 C++ project that dates back many
years. I'm running Win7 Professional 64-bit.
The top-level design of the project is this:
The code that does most of the work is encapsulated in COM DLLs.
For each DLL there's a separate wrapper function that calls:
(1) CoInitialize
(2) CoCreateInstance
(3) CoUninitialize
There's a main program that presents a dialog to allow a user to select an option. Based on the selected option, the main program calls the appropriate wrapper function, which then runs the code in the corresponding COM DLL.
Problem Details:
(1) I've been unable to step through the code in the Visual Studio debugger.
(Trying to run in the debugger produces the error "Unable to start program
", where the named DLL is different from the modified one.)
(2) I put "fprintf(stderr, ...)" calls in the modified DLL code, but didn't get any output from the "fprintf" calls. (I do see output from "fprintf" calls I added to the wrapper function that invokes the DLL.)
I also tried opening a temporary debug file using "fopen", writing debug statements to the file, then fflush, and fclose. Also no output.
(3) I noticed a post (Calling fprintf from dynamic library (c++)) that suggested that, although "fprintf(stderr, ...)" should work, it would be better to implement a callback to a debug function in the main program. I attempted to do that.
The changes compile, but the linker reports an undefined reference to the name of the function in the DLL that was intended to allow the main program
to pass in a pointer to a callback function.
I'm confused by the undefined reference, because the modified DLL has a different exported function that the linker is able to resolve.
Specifically:
__declspec(dllexport) void SetLogFunc(LogFunc LogFuncPtr) [The new function.]
__declspec(dllexport) BOOL DoRosSum(SRosSumData* pRosSumData) [The existing function.]
I used the "ack" utility to search the entire codebase for the project,
including Visual Studio project files and binary files, looking for
references to "DoRosSum", and can't find any place where there's a reference
to "DoRosSum", but not also a reference to "SetLogFunc".
("SetLogFunc" is listed by "dumpbin" as an exported function.)
I should also mention that I reverted all my changes except for:
the "SetLogFunc" function in the COM DLL,
the callback debug function in the main program, and
the call to ""SetLogFunc"" in the main program.
so I don't think the problem I'm having getting debug output, or running in the VS2012 debugger, is related to the modification I originally made to the DLL code.
Apologies for the long post. In recent years I've mostly been working in C#, or working on linux systems. I have no experience with COM DLLs, so I may be
missing something simple.
If anyone has any thoughts on how to proceed I would appreciate it.
For the first question,
https://learn.microsoft.com/en-us/visualstudio/debugger/how-to-debug-from-a-dll-project?view=vs-2017
I think you can check if you have done this yet. Usually, if you haven't set up command correctly in project property/debugging, running debugger in VC always show you the message:
Unable to start program '......\your DLL'.
Since DLL need to be execute with an executable(.exe).
I noticed that you said the error message 'the named DLL is different from the modified one'.
Your main program will run with multiple DLL right? I think you also need to make sure you put other DLL(.dll) file in the folder of your main program application.
For undefined reference issue,
If you can compile the functions in DLL sides, it means the logic here is ok. However, linker report undefined error then it should be some issues for exporting this function to main program side.
I suppose you to first check in main program side to see if you include the correct header file.
Like right clicking the function name in main program "Go to Definition" will show you the header file. You can then see if the header file is the correct one.
Then you can check if you export functions correctly. You need to make sure main program link to the new compiled Object File Library(.lib). Every time you compile your DLL project you need to make sure main program link to the new compiled .lib and .dll and include the new header file.
Hope these helps.
ProblemI'm unable to load and call methods in a compiled c class into a leiningen project. My basic approach is to load a Java class, JavaWrapper.java, that uses JNI to call some native methods in the native code, wrapper.o and then call the methods through this java wrapper class.
I imagine there are classLoader issues with loading a java class which loads the native code from a clojure project, but given that I can't seem to directly get clojure code to find the wrapper.o on the library path, I'm not sure how to handle this.
lein project file
(defproject lein-native-test "0.1.0-SNAPSHOT"
...
:java-source-paths ["java-path"]
:jvm-opts ["-Djava.library.path=.:./native:/absolute/path/to/native"] ;;not sure what format it wants
)
clojure file with main method
I've tried it slightly modified with four approaches, all included in code below along with respective error in comments.
(ns lein-native-test.core
(:import (com.test JavaWrapper)))
(def -main []
;;four things I've tried and their errors
(clojure.lang.RT.load "/abs/path/to/wrapper.o") ;;could not find file /abs/path/wrapper.o_init.class or wrapper.o.clj
(clojure.lang.RT.loadLibrary "wrapper.o") ;;UnsatisfiedLinkError no wrapper.o in java library path
(JavaWrapper/load "/abs/path/to/wrapper.o") ;;UnsatisfiedLinkError com.test.JavaWrapper.setup()
(assembly-load "/abs/path/to/wrapper.o") ;;unable to resolvesymbol: assembly-load
)
Java code with native methods that uses JNI, JavaWrapper.java
public class JavaWrapper{
public native void setup();
public static void load(String lib){ System.load(lib);}
}
Before trying to get this to work with clojure and lein I did successfully load and use the native methods in wrapper.o via JavaWrapper and JNI.
Possibly related: I'm also unable to load wrapper.o in JavaWrapper.java via
System.loadLibrary("wrapper.o");
I have to use
System.load("/absolute/path/to/wrapper.o");
Versions of tools
clojure version: 1.5.1
lein version: 2.3.4
jdk: 1.7
os: debian7
A better understanding of ClassLoaders or especially a working simple example would be very useful, thanks.
The problem was due to an naming error in my method in the C header and source files per the jni standard. The correct way to use jni with clojure is to create a Java wrapper class as I have done and load the dynamic library with the method
clojure.lang.RT.loadLibrarySince I've had trouble finding good examples for this I've made a demo on github
Errors
1) (clojure.lang.RT.load "/abs/path/to/wrapper.o") ;;could not find file /abs/path/wrapper.o_init.class or wrapper.o.clj
This load method is not meant to be used for native code, its expecting a java class or a clj file
2) (clojure.lang.RT.loadLibrary "wrapper.o") ;;UnsatisfiedLinkError no wrapper.o in java library path
Clojure is unable to find the library at link time, hence UnsatisfiedLinkError --- this is due to a naming error
first the library should be compiled as a dynamic shared library, i.e. for the gcc compiler use the -shared flag (I actually did but didn't name the output file with the normal .so extension)
java and thus clojure expect the native library to be named in a very specific way: libwrapper.so (or .jnilib for mac or .dll for windows but always with "lib" prefix)
3) (JavaWrapper/load "/abs/path/to/wrapper.o") ;;UnsatisfiedLinkError com.test.JavaWrapper.setup()
This time the error is on a method within JavaWrapper in the file or library, thus you know that at least it found the file. An UnsatisfiedLinkError that specifies a specific method in the Java class, like this one, should always be due to a naming error between what is declared a native method in the Java file and what is actually present in the c source or header file.
Note the namespace "com.test"
When declaring a jni method in c the method name must follow a specific format,
from http://docs.oracle.com/javase/7/docs/technotes/guides/jni/spec/design.html
"Dynamic linkers resolve entries based on their names. A native method name is concatenated from the following components:"
the prefix Java_
a mangled fully-qualified class name
an underscore (_) separator
a mangled method name
for overloaded native methods, two underscores (__) followed by the mangled argument signature
In this case the full c source method signature would be
void Java_com_test_setup(JNIEnv *env, jobject obj)
4) (assembly-load "/abs/path/to/wrapper.o") ;;unable to resolvesymbol: assembly-load
This method too is not meant to load native code
I am interested in using my static lib to create a dll (implicitly linking). which means I need to (in vs2008)
create a dll project that should generate the following:
header file (which have export function declarations. These are simple wrappers to actual functions in the static lib using __declspec(dllexport) which are in the .cpp )
import lib which will be made as a result of creating the dll
the actual dll which is created.
I have made a test program that will utilize the above dll(including the import lib/header files) to test it.
in this I have included all the three items. now the exe compiles/links without issue.
however in the main.cpp when i call the exported functions (with the associated __declspec(dllimport) call it never seems to execute. I am uncertain why this is?
Its almost like the even though the exe can see the exported function in in the dll...the dll cannot call on the code that is in the static lib?
i just cannot answer why my exe can't see the code in the static lib? do i need an archiver/librarian for vs2008 to include all those obj files as part of the import lib?
I am at a loss and am not sure how to test this?
other than just making my static lib directly into a dll. I wanted to try this method. I know i am missing something...i have read all over the place and i am just stuck. There were some threads here that had some people posting something similar but i can't seem to get it. please be as detailed as possible as I am new to this. thanks again.
update 1:
ok so currently i added the extern line to the function prototype and now it sees the exported function from the dll. however, now the only issue left is that:
i can't invoke the function that this exported function (aka wrapper) is trying to call. which happens to be in the static library. how should my exe get visibility to that static library function. I know it can be done because I think there was one other person on this board who was able to make this work.
update 2: my setup is exactly like this questioner...
How to force inclusion of an object file in a static library when linking into executable?
but i am not using explicit linking. i am using implicit linking. my real issue is how to call a static lib function in my dll wrapper which is exported to the exe?
If the app and DLLs are MFC app/dlls, then make sure that the application and all dlls are either "Debug" versions or "release" versions and not a mix.
I build an application in Borland C++ 6 and I'd like to import external, non Borland library (FFTW, to be exact, http://www.fftw.org).
I have downloaded the fftw dll file, used the implib.exe program to build a lib file known to Borland, included fftw.h in source and copied fftw.h to Borland/include, fftw.lib to Borland/lib and .h, .dll and .lib files to my project folder.
Unfortunately I get several linker errors, which claims:
Unresolved external '{name of the FFTW function}' referenced from {name of the source file}
What do I do wrong?
I'm just telling from a similar story how I managed to get it to work...
There was a DLL that worked (was being sucessfully imported) with Delphi 7, VB.NET and Java. I wanted to make a program with Borland C++ Builder 6 with it. I had the function prototypes and the exact declarations that made the import on those languages. Reasonable?
I thought it would be easy, but I stucked on many dead ends without sucess, with step by step "blind" guides that didn't worked for me. And the IDE or command outputs not helping either.
After a few days I tried (from question 4599357, although the DLL isn't in Visual C++):
using "implib" without "-a" and
having the prototypes declared like this:
extern "C" __declspec(dllimport) __stdcall int someDll_someFunction(someTypes someArgs, ...);
Note that the normal function prototype is at the end. If you have the "normal" prototypes, just add "extern "C" __declspec(dllimport) __stdcall" before them to your source code or header file. :) And I only have functions that return "int", this is why I put "int" there.
I think you're only missing one step... add the .lib file that implib created to your project.
Are you sure that Borland is doing proper name-mangling of the external functions, and that the header has been surrounded with extern "c" {}? And are you sure that Borland is indeed trying to link with the .lib file? Make sure the compiler has the verbose option set.
If that doesn't work, why don't you build FFTW from source instead of using a DLL?
So, I have an interesting issue. I am working with a proprietary set of dlls that I ,obviously, don't have the source for. The goal is to write an intermediate dll that groups together a large series of funnction calls from the proprietary dlls. The problem I am having, when compiling with g++, is that I get errors for the original dlls along the lines of:
cannot export libname_NULL_THUNK_DATA. Symbol not found.
If I add a main and just compile to an executable everything works as expected. I'm using mingw for compilation. Thanks for any help.
In response to the first reply: Either I'm confused about what you're saying or I didn't word my question very well. I'm not explicitly trying to export anything from my wrapper I am just calling functions from their dlls. The problem is that I get errors that it can't export these specific symbols from the dll to my wrapper. The issue is that I'm not even entirely sure what these _NULL_THUNK_DATA symbols are for. I did a search and read somewhere that they shouldn't be exported because they're internal symbols that windows uses. I have tried using the --exclude-symbols directive to the linker but it didn't seem to do anything. I apologize if I'm completely misunderstanding what you're trying to say.
So, I think my issue was related to this. When just compiling a standard executable that uses a dll I was able to include the headers and directly call the functions for example:
#include :3rdparty.h
int main(){
dostuff(); // a function in the 3rdparty.dll
}
this would compile and run fine. I just needed to link the libraries in the g++ command.
When linking with the -shared flag I would get these errors (with main removed of course). I think it has something to do with the fact that by default g++ attempts to import all symbols from the dll. What I didn't understand is why this happens in the dll vs in an executable. I will try doing it using GetProcAddress(). Thank you!
it should be as easy as you think it should be.
eg:
your dll code needs:
void doStuff()
{
3rdparty.login();
3rdparty.dostuff();
3rdparty.logoff();
};
so far - so good, you've included the right headers .... (if you have them, if you don't then you need to import the library using LoadLibrary(), then create a function pointer to each exported dll entrypoint using GetProcAddress() and then call that function pointer)
You then link with the 3rd party lib and that's it. Occasionally you will have to wrap the definitions with 'extern "C"' in order to get the linkage name mangling correct.
As you say you're using g++, you can't be getting confused with __declspec(dllimport) which is a MS VC extension.
"Compiling" tells me that you're approaching this from the wrong end. Your DLL should not export its own wrapper functions, but directly refer to exports from other DLLs.
E.g. in a Windows Kernel32.DEF file, the following forward exists:
EXPORTS
...
HeapAlloc = NTDLL.RtlAllocHeap
There's no code for the HeapAlloc function.