【问题标题】:CMake could not find JNICMake 找不到 JNI
【发布时间】:2018-12-05 11:24:56
【问题描述】:

我创建了一个支持 C++ 的新 Android Studio 项目,但没有向其中添加任何内容。该项目使用 CMake 构建、编译和运行。然后我将以下两行代码添加到文件底部的CMakeLists.txt 中,我得到了一个 CMake 构建错误。

find_package(Java COMPONENTS Development)       # Line 47
find_package(JNI REQUIRED)                      # Line 48

这是我在构建项目时遇到的错误

-- Found Java: /usr/lib/jvm/java-10-oracle/bin/java (found version "10.0.1") found components:  Development 
-- Configuring incomplete, errors occurred!
CMake Error at /home/xxxxx/Android/Sdk/cmake/3.6.4111459/share/cmake-3.6/Modules/FindPackageHandleStandardArgs.cmake:148 (message):
  Could NOT find JNI (missing: JAVA_AWT_LIBRARY JAVA_JVM_LIBRARY
See also "/home/xxxxx/AndroidStudioProjects/MyApplication/app/.externalNativeBuild/cmake/release/x86_64/CMakeFiles/CMakeOutput.log".
  JAVA_INCLUDE_PATH2 JAVA_AWT_INCLUDE_PATH)
Call Stack (most recent call first):
  /home/xxxxxx/Android/Sdk/cmake/3.6.4111459/share/cmake-3.6/Modules/FindPackageHandleStandardArgs.cmake:388 (_FPHSA_FAILURE_MESSAGE)
  /home/xxxxxx/Android/Sdk/cmake/3.6.4111459/share/cmake-3.6/Modules/FindJNI.cmake:314 (FIND_PACKAGE_HANDLE_STANDARD_ARGS)
  CMakeLists.txt:48 (find_package)
External native generate JSON release: JSON generation completed with problems

CMake 在从命令行调用时运行,但由于某种原因在 Android Studio 中失败,我不知道为什么。

编辑 1

这是CMakeOutput.log 文件

编辑 2

这就是CMakeLists.txt 文件中的全部内容。它使用命令 cmake 在 cmd 中编译。

cmake_minimum_required(VERSION 3.4.1)

find_package(Java COMPONENTS Development)
find_package(JNI REQUIRED)

这是 cmd 输出

    E:\Users\xxxxx\AndroidStudioProjects\MyApplication\app\build>cmake ..
-- Configuring done
-- Generating done
-- Build files have been written to: E:/Users/xxxxx/AndroidStudioProjects/MyApplication/app/build

当我尝试使用 gradle 在 Android Studio 中添加它时,我在 Windows 10 pro 64 位上收到以下错误

Microsoft Windows [Version 10.0.17134.112]
(c) 2018 Microsoft Corporation. All rights reserved.

E:\Users\xxxxx\AndroidStudioProjects\MyApplication>gradlew build --stacktrace

> Task :app:generateJsonModelDebug 
External native generate JSON debug: starting JSON generation
External native generate JSON debug: using platform version 24 for ABI ARMEABI_V7A and min SDK version 24
External native generate JSON debug: noticing that build file 'E:\Users\xxxxx\AndroidStudioProjects\MyApplication\app\CMakeLists.txt' is out of date with respect to E:\Users\xxxxx\AndroidStudioProjects\MyApplication\app\.extern
alNativeBuild\cmake\debug\armeabi-v7a\android_gradle_build.json
External native generate JSON debug: rebuilding JSON E:\Users\xxxxx\AndroidStudioProjects\MyApplication\app\.externalNativeBuild\cmake\debug\armeabi-v7a\android_gradle_build.json due to:
External native generate JSON debug: - a dependent build file changed
External native generate JSON debug: keeping json folder 'E:\Users\xxxxx\AndroidStudioProjects\MyApplication\app\.externalNativeBuild\cmake\debug\armeabi-v7a' but regenerating project
External native generate JSON debug: executing cmake Executable : E:\Android\SDK\cmake\3.6.4111459\bin\cmake.exe
arguments :
-HE:\Users\xxxxx\AndroidStudioProjects\MyApplication\app
-BE:\Users\xxxxx\AndroidStudioProjects\MyApplication\app\.externalNativeBuild\cmake\debug\armeabi-v7a
-DANDROID_ABI=armeabi-v7a
-DANDROID_PLATFORM=android-24
-DCMAKE_LIBRARY_OUTPUT_DIRECTORY=E:\Users\xxxxx\AndroidStudioProjects\MyApplication\app\build\intermediates\cmake\debug\obj\armeabi-v7a
-DCMAKE_BUILD_TYPE=Debug
-DANDROID_NDK=E:\Android\SDK\ndk-bundle
-DCMAKE_CXX_FLAGS=
-DCMAKE_TOOLCHAIN_FILE=E:\Android\SDK\ndk-bundle\build\cmake\android.toolchain.cmake
-DCMAKE_MAKE_PROGRAM=E:\Android\SDK\cmake\3.6.4111459\bin\ninja.exe
-GAndroid Gradle - Ninja
jvmArgs :


CMake Error at E:/Android/SDK/cmake/3.6.4111459/share/cmake-3.6/Modules/FindPackageHandleStandardArgs.cmake:148 (message):
  Could NOT find JNI (missing: JAVA_AWT_LIBRARY JAVA_JVM_LIBRARY
  JAVA_INCLUDE_PATH2 JAVA_AWT_INCLUDE_PATH)
Call Stack (most recent call first):
  E:/Android/SDK/cmake/3.6.4111459/share/cmake-3.6/Modules/FindPackageHandleStandardArgs.cmake:388 (_FPHSA_FAILURE_MESSAGE)
  E:/Android/SDK/cmake/3.6.4111459/share/cmake-3.6/Modules/FindJNI.cmake:314 (FIND_PACKAGE_HANDLE_STANDARD_ARGS)
  CMakeLists.txt:4 (find_package)
-- Configuring incomplete, errors occurred!
See also "E:/Users/xxxxx/AndroidStudioProjects/MyApplication/app/.externalNativeBuild/cmake/debug/armeabi-v7a/CMakeFiles/CMakeOutput.log".

【问题讨论】:

  • 这个问题和你的previous one有什么不同?
  • 因为最后一个试图编译一个具有 Java 绑定依赖项的 GitHub C++ 存储库,而这个只是想弄清楚为什么 CMake 不会在 Android Studio 中找到 JNI。
  • 在配置输出中,See also 消息不应破坏“缺失”变量列表。
  • 对不起,我不太明白你的评论。什么不应该破坏?
  • Lines Could NOT find JNI (missing: JAVA_AWT_LIBRARY JAVA_JVM_LIBRARY, JAVA_INCLUDE_PATH2 JAVA_AWT_INCLUDE_PATH) compound single message,因此它们之间不应出现“另请参阅”行。在您之前(已删除)的问题中可以观察到正确的行顺序。

标签: java android c++ cmake


【解决方案1】:
Could NOT find JNI (missing: JAVA_AWT_LIBRARY JAVA_JVM_LIBRARY

解决了

sudo apt-get install -y openjdk-8-jdk
sudo apt-get install -y default-jdk
export JAVA_HOME=/usr/lib/jvm/java-8-openjdk-amd64

【讨论】:

  • 截至 2020 年 2 月,它看起来仍然是 openjdk-8-jdk
  • 如果这对您不起作用,请尝试使用 -DBUILD_JAVA=ON 重新运行,例如 cmake .. -DBUILD_GSTREAMER_PLUGIN=ON -DBUILD_JNI=TRUE -DBUILD_JAVA=ON
  • yum install java-latest-openjdk-devel 在我的 CentOS 服务器上
【解决方案2】:

正如与 Android 捆绑的 CMake 版本试图告诉您的那样,它找不到 JNI 包,因为缺少某些部分:

缺少:JAVA_AWT_LIBRARY JAVA_JVM_LIBRARY JAVA_INCLUDE_PATH2 JAVA_AWT_INCLUDE_PATH

查看 FindJNI (https://cmake.org/cmake/help/latest/module/FindJNI.html) 的文档,这些变量设置为 Android 版本的 JNI 未附带的库和标头的位置(毫不奇怪,例如,Android 不包含 AWT 库)。 在运行find_package(JNI REQUIRED) 时,FindJNI 代码会检查这些变量是否已设置,如果未设置,则会发出错误。

一种解决方法是在调用find_package之前自己设置这些变量:

# We are only interested in finding jni.h: we do not care about extended JVM
# functionality or the AWT library.
set(JAVA_AWT_LIBRARY NotNeeded)
set(JAVA_JVM_LIBRARY NotNeeded)
set(JAVA_INCLUDE_PATH2 NotNeeded)
set(JAVA_AWT_INCLUDE_PATH NotNeeded)
find_package(JNI REQUIRED)

但请注意,您的代码将只能使用 jni.h 及其功能:如果它尝试访问 JNI 包的任何其他部分,它将失败(可能在编译时) 因为本质上,您已经欺骗 CMake 以为找到了整个包,而实际上只有一部分存在于 Android 设置中。

【讨论】:

  • 非常感谢您的另一个NotNeeded cmake voodoo。 if it tries to access any other part of of the JNI package ... 是什么意思?我只对将我的C++ 连接到JavaJNI 感兴趣。除了允许C++ 链接到Java 之外,JNI 还提供了什么??
  • 如果您只需要 JNI 标头就可以了。另一方面,如果您需要链接JAVA_JVM_LIBRARYJAVA_AWT_LIBRARY 或包含来自JAVA_AWT_INCLUDE_PATH 的标头,则这些将失败。 FindJNI.java 可能应该为此更新,因为现在 OP 的错误似乎相当标准。
【解决方案3】:

我找到了适合我的解决方案:

cmake_minimum_required(VERSION 3.10)
project("ktaglib")

set(JAVA_AWT_LIBRARY "$ENV{JAVA_HOME}/lib/libjawt.so")
set(JAVA_JVM_LIBRARY "$ENV{JAVA_HOME}/lib/server/libjvm.so")


set(JAVA_INCLUDE_PATH "$ENV{JAVA_HOME}/include")
set(JAVA_INCLUDE_PATH2 "$ENV{JAVA_HOME}/include/linux")
set(JAVA_AWT_INCLUDE_PATH "$ENV{JAVA_HOME}/include")

find_package(JNI REQUIRED)

您必须在环境变量中的 JAVA_HOME="/usr/lib/jvm/java-11-openjdk-amd64" 之前设置,例如

更多信息:https://github.com/dockcross/dockcross/issues/576

【讨论】:

    【解决方案4】:

    在 alpine:edge docker 镜像上也是如此,使用以下方法修复:

    ENV JAVA_HOME=/usr/lib/jvm/java-1.8-openjdk
    RUN apk add --no-cache openjdk8
    

    参考:https://pkgs.alpinelinux.org/contents?branch=edge&name=openjdk8&arch=x86_64&repo=community

    【讨论】:

      猜你喜欢
      • 2019-05-21
      • 1970-01-01
      • 1970-01-01
      • 2016-01-19
      • 1970-01-01
      • 1970-01-01
      • 2016-04-14
      • 2021-07-23
      • 2011-08-20
      相关资源
      最近更新 更多