I'm working with some java code wich loads an unmanaged dll, just as the following:
public void Foo(){
System.loadLibrary("absolute_path_to_my_dll.dll")
}
It works fine from eclipse or console.
Next step: I'm using IKVM tools to get a managed dll from my java app (ikvmc.exe). Everything works fine and my dll is built perfectly. In fact, I've imported that library in a Test Solution (and I've add all IKVM refereces needed -IKVM.Core.JDK, IKVM.Runtime.JNI, etc-).
Well, here is the problem: when I run C# code the java call to System.loadLibrary(...) fails and I get an "UnsatisfiedLinkError: Can't load absolute_path_to_my_dll.dll". Absolute path is ok and dll is there.
Any help? Thanks in advance.
Edit 1
I'll try to explain more in detail:
Java step
public void Foo(){
System.loadLibrary("absolute_path_to_my_dll.dll")
}
If path is not correct this call gives the "UnsatisfiedLinkError" mentioned above. This is not the case, everything works well. The dll file is a 32 bit one, so I compiled this java project with jre7 x86 (in 64 bit mode loadLibrary call falis, obviously, saying we can't load 32 bit dll in 64 bit AMD machine).
Ikvm step
Now I compile java code in a managed dll wich can be imported in a .net project. First of all I export my java project to a jar file, "myJar.jar". Then i apply ikvmc.exe to generate a managed dll, let's say "myNewDll.dll".
ikvm.exe -target:library -out:"myNewDll.dll" "myJar.jar"
This step works nicely and i get a new dll I can import in my VS project.
C# step
Now I create a new VS tester solution. I add "myNewDll.dll" as reference so I can use it in my C# code. Also, I add IKVM.Core.JDK reference (if not, project can't compile) and configure project in 32 bit mode. Problems start here:
Running this setup gives "IKVM.Runtime.JNI error". I've added that reference.
Running again gives "can't find ikvm-native". As I can't add ikvm-native-win32-x86.dll or ikvm-native-win32-x64.dll as reference I put both of them in output path (bin/Debug).
Next try it gives the "UnsatisfiedLinkError: Can't load xxx.dll".
How can it be possible if that dll is loaded flawlessly in java step?
Annother try
Just before start crying I tried annother way: I created a java main program that only called Foo(). Then I generated an executable file with ikvmc.exe tool and called it in windows console. It gave me the same error, UnsatisfiedLinkError so maybe it's ikvmc.exe problem but I can't understand why.
Any idea?
Edit 2
Good news. It seems I've solved the problem. First of all, I had to add -platform:x86 to ikvmc.exe call (step 2). The dll generated was succesfully imported in my C# project and it works fine if we run in execution mode (NOT debugging). If I try to debug in VS it gives me System.Runtime.InteropServices.SEHException.
Is there any kind of bug related to debugging native code (dll loaded in java code) under native code (that java code loaded in C# using ikvm)?
Is your dll a 32 bit and you run it on a 64 bit platform?
If yes then the problem is that IKVM is platform independent. This means on a 64 bit system it runs 64 bit process.
To solve this you need a 64 bit version of your dll or mark ikvm.exe as 32 bit process.
Adding an option of reference to IKVM.OpenJDK.Core.dll at ikvm's /bin directory will resolve the error.
Maybe the .jar file needs some native DLLs, which was same as Native library location parameter of JAR in Eclipse. If so, find the native DLLs and copy them to de /bin directory of IKVM, and make ikvmc to load them automatically.
That's all what I've found out. Try and see if it would bring some ideas.
Related
Update: The problem was solved with the help of MathWorks. I've published the answer below.
I need to control a program (Zemax) from Matlab. Unfortunately, Zemax only supports DDE for such control, which Matlab does not support any more. It works, but stops working on 64 bit platform after a few (presumable 63) DDE calls.
I wonder if there are working solutions. I could probably program a DLL with correct DDE support and then use DDE in Matlab via this DLL. This is a major effort for me. A more suitable solution would be to use Java DDE methods. Following another post here, I've discovered the JDDE library. However I cannot make it work: Even if I am in the directory with the DLL and JAR files, executing
import pretty-tools.JDDE-2.0.3.*
works fine but calling
a = com.pretty_tools.dde.client.DDEClientConversation()
afterwards (as done here) results in
Undefined variable "com" or class "com.pretty_tools.dde.client.DDEClientConversation".
I have very limited writing privileges on my PC, so I have added the javaclasspath.txt file with the jar/dll location to the directory indicated by prefdir. The file looks like this:
C:\Users\xxxxxxxx\Documents\matlab toolbox\jdde\pretty-tools-JDDE-2.0.3.jar
Calling javaclasspath shows a long listing with the last lines being:
...
C:\Program Files\MATLAB\R2012b\java\jarext\webservices\ws_client_core\mw-service-client-core.jar
C:\Users\kkarapet\Documents\matlab toolbox\jdde\pretty-tools-JDDE-2.0.3.jar
DYNAMIC JAVA PATH
<empty>
So path seems to be set correctly. What am I doing wrong?
With the help of MathWorks support, I've found the answer. Here is how to make JDDE work with Matlab 2012b, without admin privileges:
Download and unpack JDDE files (DLLs and JAR) into some folder. Let's say it's $path-to-jdde$\.
In Matlab, type prefdir. Open the resulting directory and create two files there, javaclasspath.txt and javalibrarypath.txt.
In javaclasspath.txt, add $path-to-jdde$\pretty-tools-JDDE-2.0.3.jar.
In javalibrarypath.txt, add $path-to-jdde$\.
Restart Matlab.
Now call ddeConv = com.pretty_tools.dde.client.DDEClientConversation; and start using the created object as described in JavaDoc. E.g. to connect to Zemax, run Zemax and then in call ddeConv.connect('Zemax', 'abc').
Step 2 above can only be done starting Matlab version R2012b. With an older version, if you have the write rights on the Matlab installation directory, you should be able to replace step 2 by editing the files librarypath.txt and classpath.txt in $MATLABROOT$\toolbox\local. I could not verify it so if you confirm it please let me know in the comment below.
I know it's probably fairly simple, but I'm having some issues grasping all the different packages I need just to install GDAL and read georeferenced rasters.
So I have already had OSGEO4W installed so that there exists a folderpath as follows: C:\OsGeo4W\lib\gdal.jar as well as C:\OsGeo4W\apps\swigwin\swig.exe
I also have the version from http://vbkto.dyndns.org/sdk/ so that I have a folderpath as follows: C:\ProjectsJava\gdal\bin\gdal\java\ with a gdal.jar and a bunch of dll's. This is what is originally linked in my project's libraries.
After googling the problem, I've also added a -Djava.library.path to point to the above gdal folderpath in the project's VM options (not entirely sure what I did but didn't make a difference anyways).
Also from random googled answers I've added environment variables to windows point to this and that related to GDAL or SWIG that did nothing (so removed them for now). So I only have a PATH that points to the gdal/bin folder and a GDAL_DATA that points to the gdal/bin/gdal-data folder. If it makes any difference I have installed successfully GDAL bindings for Python and there are some of it's environment variables left over in PATH and GDAL_DATA as well to similar but different folders.
Basically the code fails to even run a gdal.Open(in_path), giving the following error which hasn't changed no matter what I did differently:
Native library load failed.
java.lang.UnsatisfiedLinkError: C:\ProjectsJava\gdal\bin\gdal\jave\gdaljni.dll: Can't find dependent libraries
java.lang.UnsatisfiedLinkError: org.gdal.gdal.gdalJNI.Open__SWIG_1(Ljava/lang/String;)J'
at org.gdal.gdal.gdalJNI.Open__SWIG_1(Native Method)
at org.gdal.gdal.gdal.Open(gdal.java:563)
at ...
Now I know I probably screwed up getting GDAL right, but to be honest the labyrinthical instructions lost me well early on. All the odd packages to adapt C++ code to Java and instructions meant for Unix/Linux have got me all mixed up now.
SOLVED
Not sure why, but reinstalling Microsoft 2010 C++ Redistributable Package x86 helped. It was already installed, did a fix installation, and that seemed to do the trick. Hope that helps anyone else with a similar issue.
I am working on a Java project in which I have to use a third party dll (let's say abc.dll). So I created a native header file using JNI.
Then I created a dll project on vs2005 (typical win32 app.) and added that header file created by JNI. I selected clr old syntax support for the project and added the abc.dll as a reference to my project.
Up to now, everything is ok. Here is the problem. I implemented the methods defined in the header file using some methods from the abc.dll. abc.dll has a class called "abc" and that's what I do:
abc *abcObj = new abc(); abcObj->callSomeMethod();
I take a build from the solution, everything is ok. But when I run my Java program, I get an error from the JVM telling that native code broke down?!?! I debugged it and the problem is in new(). It simply cannot instantiate the abcObj.
Then I tried with a c++ app using that abc.dll. It worked.
I think there must be problem with JNI or that managed/unmanaged thing. I am not really experienced at c/c++ so I don't understand so much (at least I don't have time to understand for now). Only thing I try to do is create a wrapper dll using the third party dll and use the wrapper dll in my java app.
Any help will be appreciated.
Thanks in advance...
-haydar
edit: I have all the dlls that are needed by my third party dll.
I have solved the problem. The problem was that I was creating the project as a win32 application and choosing dll then. I created a clr application and everything went well. I followed the instructions from here.
I'm on Windows 7 32bit, Java JRE6 31 installed and using Sikuli X 1.0rc3. I want to launch a test with sikuli-script.jar like this:
java -jar c:\sikuli\sikuli-script.jar test.sikuli
All I get is this error message:
java.lang.UnsatisfiedLinkError: java.lang.UnsatisfiedLinkError:C:\sikuli\libs\VisionProxy.dll: Can't find dependent libraries
I have set all the environment variables needed, so my PATH looks like this:
PATH=...;C:\sikuli\libs;C:\Program Files\Java\jre6\bin
SIKULI_HOME=C:\sikuli
I can use the IDE and launch the tests there etc. But only if I use the Sikuli-IDE.exe the sikuli-ide.bat and sikuli-ide.jar don't work either. Always with the same error from above. So I think in the build process of the .exe file they added some magic, but I can't figure out what it is.
Does somebody have a similar problem? Or even a solution?
Update
As I wrote below, it works out of the box with my new computer. :D But maybe my solution can help someone.
Sikuli Team uses Launch4J to build the Sikuli-IDE.exe out of the sikuli-ide.jar. They use this config file. I modified it slightly and created a Sikuli-script.exe. It was pretty simple but I lost the config file unfortunately.
Hope I could help!
You must use a 32bit JRE version (I use jre-7u4-windows-i586.exe)
Download Sikuli IDE for Windows (I use "Sikuli X r930", portable version)
Unpack it and copy files to your project folder (I renamed it to "sikuli-ide", check image htt+p://i.stack.imgur.com/LSiQV.png)
Add sikuli-script.jar to the Referenced Libraries (Project > Properties > Java Build Path > Libraries, check image http://i.stack.imgur.com/N2SJ8.png)
Set PATH and SIKULI_HOME environment vars (Run > Run Configurations > Environment, check image http://i.stack.imgur.com/HboXk.png)
You're ready to go ;)
According to the docs
Thrown if the Java Virtual Machine cannot find an appropriate native-language definition of a method declared native.
What you need to do is use this command:
-Djava.library.path=pathToDLL
Which will add your DLL that is missing.
I'm using the code from this tutorial for using MXJ to "embed" MySQL in my java application. However, I'm getting this exception when running the code:
Exception in thread "main" java.util.MissingResourceException: Resource '5-5-9/Windows_7-amd64/mysqld.exe' not found
This happens when I reach this line in the tutorial:
mysqldResource.start("test-mysqld-thread", database_options);
I'm running in Eclipse and I have the 4 following jars added to my build path, since this link says I need them:
mysql-connector-java-5.1.18-bin.jar
mysql-connector-mxj-gpl-5-0-12-db-files.jar
mysql-connector-mxj-gpl-5-0-12.jar
aspectjrt-1.6.9.jar
I'm not sure what I'm missing here. Any tips?
MXJ doesn't come ready for use with Windows 7 64 bit. Using this bug ticket, I found what I needed to do.
Once the files are downloaded and extracted from the zips, unjar mysql-connector-mxj-gpl-5-0-12-db-files.jar and add a line to platform-map.properties file inside:
Windows_7-amd64=Win-x86
Save, and re-jar. Works like a charm!
Actually it's never a good idea to mess up with the jar files, cause whenever you upgrade to a newer version you'll need to remember to redo this fix again. The answer is correct, but you just need to create platform-map.properties file with this inside:
Windows_7-amd64=Win-x86
and add it to your classpath.
For anyone who has the same issue on MacOS Catalina, you can follow the README.md in my repo (https://github.com/pengyue/mysql-connector-mxj-mac-os-catalina), which has the 64 bits executables for MacOS Catalina, and this improved connector works on Catalina.
To explain what I have done:
Download the 64 bits executables from MySQL to the folder 5-5-9
Add the platform mapping for 64 bits MacOS in platform-map.properties
Create a jar by using jar cvf mysql-connector-mxj-db-files-5.0.12.jar .
Replace the jar in your mvn settings folder ~/.m2/repository/mysql/mysql-connector-mxj-db-files/5.0.12/ with the jar you just created.
This solution works fine for my projects, Unfortunately I could not find a github for the mysql-connector-mxj, as it is deprecated and not maintainable anymore.
The other option is to use wix-embedded-mysql(https://github.com/wix/wix-embedded-mysql) instead of mysql-connector-mxj, but this probably requires some code changes in your projects.