Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. Mobile and Embedded
  4. Android dns resolve crash
Forum Updated to NodeBB v4.3 + New Features

Android dns resolve crash

Scheduled Pinned Locked Moved Solved Mobile and Embedded
17 Posts 4 Posters 1.7k Views 2 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • jsulmJ jsulm

    @wantfat said in Android dns resolve crash:

    I tried it just now, but the same thing happened

    How? Please show the code.

    "It also crash in the same place." - which place exactly?

    W Offline
    W Offline
    wantfat
    wrote on last edited by
    #6

    @jsulm This is the code, I check reply valid
    #include <QGuiApplication>
    #include <QQmlApplicationEngine>
    #include "QAbstractEventDispatcher"
    #include "QThread"
    #include "QTimer"
    #include "QNetworkAccessManager"
    #include "QNetworkReply"
    #include "QNetworkReply"
    #include "QHostInfo"

    int main(int argc, char *argv[])
    {
    QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);

    QGuiApplication app(argc, argv);
    
    QQmlApplicationEngine engine;
    const QUrl url(QStringLiteral("qrc:/main.qml"));
    QObject::connect(&engine, &QQmlApplicationEngine::objectCreated,
                     &app, [url](QObject *obj, const QUrl &objUrl) {
        if (!obj && url == objUrl)
            QCoreApplication::exit(-1);
    }, Qt::QueuedConnection);
    engine.load(url);
    
    for (int i = 0; i < 10; i++) {
        QThread *thr = new QThread();
        thr->start();
    
        while (!QAbstractEventDispatcher::instance(thr)) {
            thr->wait(1);
        }
    
        QMetaObject::invokeMethod(QAbstractEventDispatcher::instance(thr), [=](){
            QTimer *t = new QTimer();
            t->setSingleShot(true);
            t->start(1);
    
            QNetworkAccessManager *mgr = new QNetworkAccessManager();
            QObject::connect(t, &QTimer::timeout, [=](){
                QNetworkRequest request;
                request.setUrl(QString("http://xyz%1.cn").arg(i));
    
                QNetworkReply *reply = mgr->get(request);
                if (reply == nullptr) {
                    qDebug() << "reply is null";
                    return;
                }
    
                QObject::connect(reply, &QNetworkReply::finished, [=](){
                    reply->deleteLater();
                    t->start();
                });
            });
        });
    }
    
    return app.exec();
    

    }

    When it crash, The stack is as follows

    1 dlfree 0xb6dcbf4c
    2 free 0xb6db2258
    3 __res_ndestroy 0xb6dba4da
    4 __res_vinit 0xb6dba578
    5 QHostInfoAgent::fromName(QString const&) 0xa2aadd7e
    6 QHostInfoRunnable::run() 0xa2aa5516
    7 QThreadPoolThread::run() 0xa2e6e05e
    8 QThreadPrivate::start(void *) 0xa2e6c400
    9 __pthread_start(void *) 0xb6db659c
    10 __start_thread 0xb6db44c4
    11 ??

    1 Reply Last reply
    0
    • SGaistS Offline
      SGaistS Offline
      SGaist
      Lifetime Qt Champion
      wrote on last edited by
      #7

      Hi,

      Why are you creating 10 threads making get requests almost as fast as possible all the time your application is running ?

      On a side note, you are leaking QNetworkAccessManager and QTimer objects.

      Interested in AI ? www.idiap.ch
      Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

      W 1 Reply Last reply
      0
      • SGaistS SGaist

        Hi,

        Why are you creating 10 threads making get requests almost as fast as possible all the time your application is running ?

        On a side note, you are leaking QNetworkAccessManager and QTimer objects.

        W Offline
        W Offline
        wantfat
        wrote on last edited by
        #8

        @sgaist If I had two threads, It would still crash, just for a long time. the request is serial execution .
        thank you.

        1 Reply Last reply
        0
        • W Offline
          W Offline
          wantfat
          wrote on last edited by
          #9

          I run on another phone (Android 9, armv7) , The code work well. The mobile phone that had abnormalities is Android 5.1 armv7. I am not sure whether it depend on mobile phone .

          J.HilkJ 1 Reply Last reply
          0
          • W wantfat

            I run on another phone (Android 9, armv7) , The code work well. The mobile phone that had abnormalities is Android 5.1 armv7. I am not sure whether it depend on mobile phone .

            J.HilkJ Offline
            J.HilkJ Offline
            J.Hilk
            Moderators
            wrote on last edited by
            #10

            @wantfat you do realize that

            QThread *thr = new QThread();
                thr->start();
            
                while (!QAbstractEventDispatcher::instance(thr)) {
                    thr->wait(1);
                }
            

            is doing nothing but delay forcefully delay the loop by 1 millisecond?
            Also you don't need a QNetworkAccessManager instance for each get request. QNetworkAccessManager can handle 5 get requests in parallel, IIRC, and the rest is automatically queued


            Be aware of the Qt Code of Conduct, when posting : https://forum.qt.io/topic/113070/qt-code-of-conduct


            Q: What's that?
            A: It's blue light.
            Q: What does it do?
            A: It turns blue.

            W 1 Reply Last reply
            1
            • J.HilkJ J.Hilk

              @wantfat you do realize that

              QThread *thr = new QThread();
                  thr->start();
              
                  while (!QAbstractEventDispatcher::instance(thr)) {
                      thr->wait(1);
                  }
              

              is doing nothing but delay forcefully delay the loop by 1 millisecond?
              Also you don't need a QNetworkAccessManager instance for each get request. QNetworkAccessManager can handle 5 get requests in parallel, IIRC, and the rest is automatically queued

              W Offline
              W Offline
              wantfat
              wrote on last edited by
              #11

              @j-hilk After call QThread::start the eventDispatcher of thread is null, so must take a sleep wait for eventDispatcher be create, QNetworkAccessManager only one instance for per thread .

              J.HilkJ 1 Reply Last reply
              0
              • W wantfat

                @j-hilk After call QThread::start the eventDispatcher of thread is null, so must take a sleep wait for eventDispatcher be create, QNetworkAccessManager only one instance for per thread .

                J.HilkJ Offline
                J.HilkJ Offline
                J.Hilk
                Moderators
                wrote on last edited by
                #12

                @wantfat said in Android dns resolve crash:

                , QNetworkAccessManager only one instance for per thread

                no, from your code, you create 10 QNetworkAccessManager instances and all live inside the main(Gui) thread


                Be aware of the Qt Code of Conduct, when posting : https://forum.qt.io/topic/113070/qt-code-of-conduct


                Q: What's that?
                A: It's blue light.
                Q: What does it do?
                A: It turns blue.

                W 1 Reply Last reply
                0
                • J.HilkJ J.Hilk

                  @wantfat said in Android dns resolve crash:

                  , QNetworkAccessManager only one instance for per thread

                  no, from your code, you create 10 QNetworkAccessManager instances and all live inside the main(Gui) thread

                  W Offline
                  W Offline
                  wantfat
                  wrote on last edited by
                  #13

                  @j-hilk QMetaObject::invokeMethod(QAbstractEventDispatcher::instance(thr), ={

                  });
                  This code make sure lambda run on thr.

                  J.HilkJ 1 Reply Last reply
                  0
                  • W wantfat

                    @j-hilk QMetaObject::invokeMethod(QAbstractEventDispatcher::instance(thr), ={

                    });
                    This code make sure lambda run on thr.

                    J.HilkJ Offline
                    J.HilkJ Offline
                    J.Hilk
                    Moderators
                    wrote on last edited by
                    #14

                    @wantfat have you checked that ? by combining invokeMethod with a lambada the object reference pointer becomes a context pointer. I see no reason, why it should be called from the Thread instance, or I personally don't know, never tried threading in this unusual way.


                    Be aware of the Qt Code of Conduct, when posting : https://forum.qt.io/topic/113070/qt-code-of-conduct


                    Q: What's that?
                    A: It's blue light.
                    Q: What does it do?
                    A: It turns blue.

                    W 1 Reply Last reply
                    0
                    • J.HilkJ J.Hilk

                      @wantfat have you checked that ? by combining invokeMethod with a lambada the object reference pointer becomes a context pointer. I see no reason, why it should be called from the Thread instance, or I personally don't know, never tried threading in this unusual way.

                      W Offline
                      W Offline
                      wantfat
                      wrote on last edited by
                      #15

                      @j-hilk Yes, I have checked it, this is detail info, https://stackoverflow.com/a/21653558

                      1 Reply Last reply
                      0
                      • W Offline
                        W Offline
                        wantfat
                        wrote on last edited by wantfat
                        #16

                        The test code work well on Qt 5.12.3, The problematic version is Qt 5.12.4 . I compared two versions of the relevant code
                        0_1564538533924_QQ图片20190731100118.png
                        0_1564538549953_QQ图片20190731100124.png

                        If method __res_init resolve fail dlsym be call, and it return a valid pointer, But it is not a thread safe function. Maybe so.

                        1 Reply Last reply
                        0
                        • W Offline
                          W Offline
                          wantfat
                          wrote on last edited by
                          #17

                          I solved this problem by export thread safe __res_init

                          #if (QT_VERSION == QT_VERSION_CHECK(5,12,4))

                          #include "resolv.h"
                          #include "QMutex"

                          static QMutex mut;

                          int __res_init(void) {
                          QMutexLocker lck(&mut);
                          return res_init();
                          }

                          #endif

                          Thanks every one.

                          1 Reply Last reply
                          1

                          • Login

                          • Login or register to search.
                          • First post
                            Last post
                          0
                          • Categories
                          • Recent
                          • Tags
                          • Popular
                          • Users
                          • Groups
                          • Search
                          • Get Qt Extensions
                          • Unsolved