简体   繁体   English

Qt5 QGeoPositionInfoSource::createDefaultSource() 在 Android 5.0 上崩溃

[英]Qt5 QGeoPositionInfoSource::createDefaultSource() crashes on Android 5.0

I'm developing a Qt5 application for Android (with CMake!) and currently I'm trying to read location data using Qt's QGeoPositionInfoSource .我正在为 Android 开发一个 Qt5 应用程序(使用 CMake!),目前我正在尝试使用 Qt 的QGeoPositionInfoSource读取位置数据。 All of my application is doing fine so far but when I run到目前为止,我所有的应用程序都运行良好,但是当我运行时

auto source = QGeoPositionInfoSource::createDefaultSource(this);

The application crashes immediately and logcat gives me:应用程序立即崩溃, logcat给我:

I/__log_qt(  422): (II) dpw_qt5:    <last output from my app>
F/libc    (  422): Fatal signal 11 (SIGSEGV), code 1, fault addr 0x0 in tid 797 (QtThread)
I/DEBUG   (  333): *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** ***
I/DEBUG   (  333): Build fingerprint: 'samsung/trltexx/trlte:5.0.1/LRX22C/N910FXXU1BOE3:user/release-keys'
I/DEBUG   (  333): Revision: '12'
I/DEBUG   (  333): ABI: 'arm'
I/DEBUG   (  333): pid: 422, tid: 797, name: QtThread  >>> org.qtproject.DPW <<<
I/DEBUG   (  333): signal 11 (SIGSEGV), code 1 (SEGV_MAPERR), fault addr 0x0
I/DEBUG   (  333):     r0 00000000  r1 9d2bedf8  r2 00010006  r3 be7eb61d
I/DEBUG   (  333):     r4 9d2bedf4  r5 9d2bedf8  r6 00000000  r7 9cffa030
I/DEBUG   (  333):     r8 9d2bedf4  r9 afd04388  sl 00000001  fp 9d2bf8dc
I/DEBUG   (  333):     ip 9cff9e80  sp 9d2bedd0  lr 9cff49b7  pc 9cff612e  cpsr 60070030
I/DEBUG   (  333): 
I/DEBUG   (  333): backtrace:
I/DEBUG   (  333):     #00 pc 0000512e  /data/data/org.qtproject.DPW/qt-reserved-files/plugins/position/libqtposition_android.so
I/DEBUG   (  333):     #01 pc 000039b3  /data/data/org.qtproject.DPW/qt-reserved-files/plugins/position/libqtposition_android.so

I've used the last three Android NDKs and several versions of Qt from 5.6 to 5.9 - all with the same result so I think I'm doing something wrong systematically.我使用了最后三个 Android NDK 和 Qt 从 5.6 到 5.9 的几个版本——结果都一样,所以我认为我系统地做错了什么。

My AndroidManifest.xml contains the following lines:我的AndroidManifest.xml包含以下几行:

<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />

Do you have any idea for me where I can start to investigate?你知道我可以从哪里开始调查吗?

Update:更新:

I've been tracing back the top most line of the call stack:我一直在追溯调用堆栈的最顶层行:

I/DEBUG   (  333):     #00 pc 0000512e  /data/data/org.qtproject.DPW

and I found out that the following line inside jnipositioning.cpp causes the crash:我发现jnipositioning.cpp中的以下行导致崩溃:

if (javaVM->GetEnv((void**)&jniEnv, JNI_VERSION_1_6) < 0) {

so the new question is: what can make javavm->GetEnv() (declared in jni.h ) crash?所以新的问题是:什么可以使javavm->GetEnv() (在jni.h中声明)崩溃?

Another Update:另一个更新:

jpo38 pointed out that that building with qmake results in an Android app that does not crash. jpo38指出,使用 qmake 构建的 Android 应用程序不会崩溃。 I've set up a github project demonstrating this behavior.我已经建立了一个github 项目来演示这种行为。

So the question is now: What's the difference between the apps being configured with CMake and qmake?所以现在的问题是:配置CMake和qmake的app有什么区别?

This apparently works pretty well: 这显然效果很好:

TestGeo.pro: TestGeo.pro:

QT += core gui
QT += positioning
QT += widgets

TARGET = TestGeo
TEMPLATE = app

SOURCES += main.cpp

CONFIG += mobility
MOBILITY = 

main.cpp: main.cpp中:

#include <QMainWindow>
#include <QApplication>

#include <QGeoPositionInfoSource>
#include <QDebug>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);

    QMainWindow w;

    qDebug() << "Creating";
    auto source = QGeoPositionInfoSource::createDefaultSource(&a);
    if ( source )
        qDebug() << "Created";
    else
        qDebug() << "NULL";

    w.show();

    return a.exec();
}

Program outputs with no crash: 程序输出没有崩溃:

Creating
Created

Note that I added no AndroidManifest.xml file to the project. 请注意,我没有向项目添加AndroidManifest.xml文件。 It works both with "Localisation" enabled or disabled. 它既可以启用也可以禁用“本地化”。

I'm deploying with Android-22 target on Nexus 6 with Android 5.1 ( armeabi-v7a ). 我正在使用Android 5.1armeabi-v7a )在Nexus 6上部署Android-22目标。 Using Qt 5.6 ( GCC 4.9 ). 使用Qt 5.6GCC 4.9 )。 Using NDK r11b . 使用NDK r11b

There must be something wrong with your setup. 您的设置一定有问题。

So do this setup, generate the working apk. 所以做这个设置,生成工作apk。 Then extract the content of this working apk and your failing apk. 然后提取这个工作apk的内容和你失败的apk。 By checking the differences (missing libraries, files, different manifest....), you may identify what's wrong with your CMake build and deployment environment and later fix it (possibly by manually copying missing files in the CMake project)! 通过检查差异(缺少库,文件,不同的清单......),您可以确定您的CMake构建和部署环境有什么问题,然后再修复它(可能通过手动复制CMake项目中的丢失文件)!

In your case the references to Qt's positioning libraries are missing. 在您的情况下,缺少对Qt定位库的引用。 Just add them correctly to your AndroidManifest.xml : 只需将它们正确添加到AndroidManifest.xml

<meta-data android:name="android.app.load_local_libs" android:value="plugins/platforms/android/libqtforandroid.so:plugins/position/libqtposition_android.so"/>
<meta-data android:name="android.app.load_local_jars" android:value="jar/QtAndroid.jar:jar/QtAndroidAccessibility.jar:jar/QtAndroid-bundled.jar:jar/QtAndroidAccessibility-bundled.jar:jar/QtPositioning.jar:jar/QtPositioning-bundled.jar"/>
<meta-data android:name="android.app.static_init_classes" android:value="org.qtproject.qt5.android.positioning.QtPositioning:org.qtproject.qt5.android.positioning.QtPositioning"/>

if crashed in runtime check this:如果在运行时崩溃检查这个:

CMakeLists.txt CMakeLists.txt

find_package(QT NAMES Qt6 Qt5 COMPONENTS Core Positioning REQUIRED)
find_package(Qt${QT_VERSION_MAJOR} COMPONENTS Core Positioning REQUIRED)
target_link_libraries(PositioningAndroidTest PRIVATE Qt${QT_VERSION_MAJOR}::Positioning)

AndroidManifest.xml AndroidManifest.xml

<meta-data android:name="android.app.qt_libs_resource_id" android:resource="@array/qt_libs"/>
<meta-data android:name="android.app.load_local_libs_resource_id" android:resource="@array/load_local_libs"/>
<meta-data android:name="android.app.load_local_jars" android:value="jar/QtAndroid.jar:jar/QtAndroidExtras.jar:jar/QtPositioning.jar"/>
<meta-data android:name="android.app.static_init_classes" android:value="org.qtproject.qt5.android.positioning.QtPositioning"/>

and res/values/libs.xml和 res/values/libs.xml

    <array name="qt_libs">
        <item>armeabi-v7a;Qt5Positioning_armeabi-v7a</item>
    </array>

    <array name="load_local_libs">
        <item>armeabi-v7a;libplugins_platforms_qtforandroid_armeabi-v7a.so:libplugins_position_qtposition_android_armeabi-v7a.so</item>
    </array>

And this code work fine:这段代码工作正常:

QGeoPositionInfoSource *source = QGeoPositionInfoSource::createDefaultSource(this);
if (source)
{
  connect(source, SIGNAL(positionUpdated(QGeoPositionInfo)), this, SLOT(positionUpdated(QGeoPositionInfo)));
  source->setUpdateInterval(1000);
  source->startUpdates();
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM