簡體   English   中英

JNI%1無效的Win32應用程序

[英]JNI %1 is not a valid Win32 application

我正在使用JDK 1.7_25(64位)在64位Windows 8上運行Netbeans,並遵循以NetBeans開頭JNI的說明( https://netbeans.org/kb/docs/cnd/beginning-jni- linux.html

這些說明適用於linux,但我認為適用於Windows的原理相同(生成.dll文件而不是.so,使用JDK中的win32等生成)

我安裝了Cygwin64以及Cygwin32。 使用Cygwin64,我可以從C / C ++動態庫項目中生成一個64位DLL。 但是,當我調用System.load(“ path / to / JNITest.dll”)時,我得到:

Exception in thread "main" java.lang.UnsatisfiedLinkError: C:\Users\Andrew\Documents\NetBeansProjects\JNITestLib\dist\JNITest.dll: %1 is not a valid Win32 application
at java.lang.ClassLoader$NativeLibrary.load(Native Method)
    at java.lang.ClassLoader.loadLibrary1(ClassLoader.java:1957)
    at java.lang.ClassLoader.loadLibrary0(ClassLoader.java:1882)
    at java.lang.ClassLoader.loadLibrary(ClassLoader.java:1843)
    at java.lang.Runtime.load0(Runtime.java:795)
    at java.lang.System.load(System.java:1061)
    at jnitest.JNITest.main(JNITest.java:8)
Java Result: 1

據我所知,這是在32位虛擬機上加載64位應用程序時最常見的情況,但是我的netbeans.conf指向的是64位JVM。

此外,當我使用Cygwin的32位版本進行編譯並運行時,我得到

Can't load IA 32-bit .dll on a AMD 64-bit platform

我敢肯定,我正確地生成了DLL文件,這只是遵循JNI教程的簡單HelloWorld printf。 我是JNI和C的新手,所以我不太確定從哪里開始調試。 我做過的最好的事情是同時嘗試了32位和64位DLL,並且我確保我的C編譯器(Cygwin)是64位的,而我的JVM也是如此。

我將不勝感激!

編輯:這是包含的文件

=== Java(JNITest.java)===

package jnitest;

public class JNITest {

    public static void main(String[] args) {
        System.out.println("JVM: " + System.getProperty("sun.arch.data.model"));
        System.load("C:\\Users\\Andrew\\Documents\\NetBeansProjects\\JNITestLib\\dist\\JNITest.dll");

        new JNITest().doHello();
    }

    public native void doHello();
}

===生成的javah標頭(jnitest_JNITest.h)===

/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class jnitest_JNITest */

#ifndef _Included_jnitest_JNITest
#define _Included_jnitest_JNITest
#ifdef __cplusplus
extern "C" {
#endif
/*
 * Class:     jnitest_JNITest
 * Method:    doHello
 * Signature: ()V
 */
JNIEXPORT void JNICALL Java_jnitest_JNITest_doHello
  (JNIEnv *, jobject);

#ifdef __cplusplus
}
#endif
#endif

=== C(JNITest.c)===

#include <jni.h>
#include "jnitest_JNITest.h"

JNIEXPORT void JNICALL Java_jnidemojava_Main_nativePrint
        (JNIEnv *env, jobject obj) 
{
    printf("\nHello World from C\n");

}

編輯:

問題似乎出在DLL上,因為我可以加載其他64位DLL很好。 我以為Cygwin可能是問題所在,所以我將編譯器更改為MinGW-w64。 它編譯良好,並且庫已加載,但是現在我得到一個新的異常:

Exception in thread "main" java.lang.UnsatisfiedLinkError: jnitest.JNITest.doHello()V
    at jnitest.JNITest.doHello(Native Method)
    at jnitest.JNITest.main(JNITest.java:10)
Java Result: 1

一些進一步的挖掘發現,當ClassLoader在此處讀取libs.size()時,拋出該錯誤:

// Invoked in the VM class linking code.
    static long findNative(ClassLoader loader, String name) {
        Vector<NativeLibrary> libs =
            loader != null ? loader.nativeLibraries : systemNativeLibraries;
        synchronized (libs) {
            int size = libs.size();
            for (int i = 0; i < size; i++) {
                NativeLibrary lib = libs.elementAt(i);
                long entry = lib.find(name);
                if (entry != 0)
                    return entry;
            }
        }
        return 0;
    }

編輯:答案!

終於想通了。

首先,Cygwin64出了點問題。 使用其他64位C編譯器擺脫了無效的Win32應用程序錯誤。

其次,我的JNITest.c文件的方法簽名不正確。 應該是:

Java_jnitest_JNITest_doHello

代替

Java_jnitest_Main_doHello

更改之后,它就可以了!

(盡管我不能再回答自己的問題6個小時了...所以dum de dum)

終於想通了。

首先,Cygwin64出了點問題。 使用其他64位C編譯器擺脫了無效的Win32應用程序錯誤。

其次,我的JNITest.c文件的方法簽名不正確。 應該是:

Java_jnitest_JNITest_doHello

代替

Java_jnitest_Main_doHello

更改之后,它就可以了!

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM