cuDNN wrapper?

(EDITED - See below!)

@Felix3 The stack trace should contain “two” stack traces: The message
No resource found with name ‘/lib/JCudnn-windows-x86_64.dll’
comes from the attempt to load the library from the JAR.
A few lines below that, there should be a message indicating why it failed to load it from the file system. This might already give a hint, referring to the “Types of UnsatisfiedLinkErrors” that are listed in the FAQ.

But in any case, I’ll do another test tomorrow when I’m back at my Dev-PC.

EDIT: I guess the message is “Can’t find dependent libraries”: You will also need he cuDNN library. For testing, you can just copy the cuDNN DLL library into the same directory as the JCudnn library (otherwise, you may add the directory with the cuDNN DLL to the PATH)

As mentioned before, a quick run in the debugger has showed that the DLL itself is not OK (JVM cannot load it), maybe it is corrupted or in the wrong format…?

I have downloaded and installed it again - same result.

@Felix3 Not sure whether you already saw the “EDIT”, but in any case, I’ll check this again tomorrow and drop a note here (still, the error message from the Stack Trace may be interesting)

Hi Marco,

Sorry, missed that. I have copied several other DLLs (including cuDnn) to the directory holding Cudnn-windows-x86_64.dll now,
but unfortunately the problem persists:

The exception occurs in java.lang.ClassLoader.loadLibrary0(), ClassLoader.java:1937 with details:

java.lang.UnsatisfiedLinkError: C:\Users.…\jars\lib\JCudnn-windows-x86_64.dll: Can’t find dependent libraries

stack trace (jdk 1.8.0_40):

java.lang.ClassLoader$NativeLibrary.load(Native Method)
java.lang.ClassLoader.loadLibrary0(ClassLoader.java:1937),
java.lang.ClassLoader.loadLibrary(ClassLoader.java:1855)
java.lang.Runtime.loadLibrary0(Runtime.java:870)
java.lang.System.loadLibrary(System.java:1122)
jcuda.LibUtils.loadLibrary(LibUtils.java:94)
jcuda.jcudnn.JCudnn.initialize(JCudnn.java:82)
jcuda.jcudnn.JCudnn.(JCudnn.java:70)
cuda.dnn.MnistJCudnn.main(MnistJCudnn.java:627)

here is the content of the directory holding the DLLs:

BTW, the JCuRand sample is working fine…

@Felix3 OK, I guess I know what the problem is: A dumpbin /DEPENDENTS JCudnn-windows-x86_64.dll showed that it depends on


MSVCP120.dll
MSVCR120.dll

But this should actually already be prevented by the CMake flag overrides in the jcuda-common CMake-Files. I’ll have a look to see what went wrong there.

BTW: These libraries are contained in the Microsoft Redistributables packages, but even though it should work after downloading and installing them, these libraries are a plain nuisance here and simply not required, so I’ll check why Visual Studio linked against them, and build updated JCudnn libraries without this dependency. Sorry for this hassle, by the way.

Copied both DLLs from the Microsoft Visual Studio 12.0\Common7\IDE\Remote Debugger\x64 dir to my project lib dir but the problem persists…

@Marco13 :

Found a solution: it works when cudnn64_70.dll is copied to \bin or any other directory in the system path like e. g. C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v7.5\bin, where I guess it belongs anyway…

Strangely enough it does not work when cudnn64_70.dll is simply in the same dir as JCudnn-windows-x86_64.dll, not even when java.library.path is pointing to this directory.

@Felix3 It should NOT be necessary to copy anything to the JDK folder.

In fact, it should not be necessary to copy any of the CUDA libraries anywhere: The hint of copying the cuDNN DLL into the same directory as the JCudnn DLL was only to see whether this is the missing dependency.

Usually, the directories containing the CUDA DLLs should simply be part of the PATH environment variable. For cuDNN, the case is a bit special because it is not (yet?) part of the CUDA Toolkit. So copying it to the CUDA\bin directory is at least a reasonable solution.

(I copied it into the same directory as the JCudnn DLL, and this worked properly - not sure why it didn’t work for you, but it’s not unlikely that this is due to the MSVC DLLs…)

Anyhow, I’ll have a look at the dependencies of the cuDNN DLL and the JCudnn DLL, to see whether there is something odd.

@Felix3 I have udpdated the JCudnn library to no longer depend on the MSVC libraries. More precisely: I have rebuilt all JCuda/Win64 libraries, because they all had this dependency. The CMake flag overrides that should actually have prevented this dependency had not been integrated properly into the CMake files (the includes have to appear before any project definition … CMake works in mysterious ways…)

Sorry, but the new DLL shows the same behavior as before. I also strongly doubt that the MS*120.DLLs are causing any trouble here - they’re in the system path anyway and otherwise it wouldn’t work with the cudnn64_70.dll in the CUDA\bin directory too.

[QUOTE=Marco13]
Usually, the directories containing the CUDA DLLs should simply be part of the PATH environment variable. For cuDNN, the case is a bit special because it is not (yet?) part of the CUDA Toolkit. So copying it to the CUDA\bin directory is at least a reasonable solution.[/QUOTE]

I think that’s the way to go. It should be there like the other CUDA DLLs, but the installer unfortunately does not copy it - probably because cuDNN seems to be not yet quite integrate into the CUDO Toolkit as you have said.

Could it be that it is working for you because you already have the cudnn64_70.dll elsewhere in your path? You could temporarily rename the DLL in the same directory as the JCudnn DLL for verfication.

[QUOTE=Felix3]Sorry, but the new DLL shows the same behavior as before. I also strongly doubt that the MS*120.DLLs are causing any trouble here - they’re in the system path anyway and otherwise it wouldn’t work with the cudnn64_70.dll in the CUDA\bin directory too.
[/quote]

Sure, but this dependency is not needed, so it should not be there anyhow (regardless of whether this was the reason for the problem in your case)

Could it be that it is working for you because you already have the cudnn64_70.dll elsewhere in your path? You could temporarily rename the DLL in the same directory as the JCudnn DLL for verfication.

No, I copied it there because initially, it complained about not finding a dependency :wink:

The behavior that you described is really strange - to summarize this:

  • It does NOT work when cuDNN.dll and JCudnn.dll are in the same directory which is given as java.library.path
  • It finds the JCudnn.dll when it is located in the „root“ directory where the program is run (even if it is not in the java.library.path)
  • It works when the JCudnn.dll is found (regardless of whether it is found by being in the root, or via the java.library.path) AND the cuDNN.dll is in a PATH directory

Is this correct?
(BTW: The java.library.path will not affect the dependencies, but when they are in the same directory, they should be found in any case)

One could try out different „corner cases“ now, but I’m not sure how to analyze the root cause here systematically…