Uploaded image for project: 'Qt'
  1. Qt
  2. QTBUG-85974

Allow dynamic builds of Qt for iOS

    XMLWordPrintable

Details

    • iOS/tvOS/watchOS
    • adb91d6af (dev)

    Description

      It is possible to configure Qt with -shared flag for iOS and it does produce .dylib and iOS Frameworks.

       

      But the Qt iOS platform plugin is still static (libqios.a), which makes the build not purely dynamic libs, but mostly dynamic libs with exception of a static libqios.a.

      Note: linking with libqios.a also requires linking with libQt5FontDatabaseSupport.a, libQt5ClipboardSupport.a, libQt5GraphicsSupport.a, libqtfreetype.a and libqtlibpng.a to get rid of unresolved symbols, which makes the process quite cumbersome.

       

      For example, it is possible to make a few modifications to Qt source code and change it to purely dynamic this way [tested in Qt 5.15.0]:

       

      1. Remove the line that forces libqios to be static from qtbase/src/plugins/platforms/ios/kernel.pro:

      qtConfig(shared): CONFIG += static

       

      1. Extend existing qt_main_wrapper() in qtbase/src/plugins/platforms/ios/qioseventdispatcher.mm to have a third parameter, which is a pointer to the actual main(), that must be called when initialisation is complete:

       

      @@ -213,8 +213,10 @@ void printUsage()
       
       using namespace QT_PREPEND_NAMESPACE(QtPrivate);
       
      --extern "C" int qt_main_wrapper(int argc, char *argv[])-
      +*int (*main_ptr)(int, char **) = 0;*
      +Q_EXTERN_C Q_DECL_EXPORT int qt_main_wrapper(int argc, char *argv[]*, int (*real_main_ptr)(int, char **)*)
       {
      + *main_ptr = real_main_ptr;*
       @autoreleasepool {
       size_t defaultStackSize = 512 * kBytesPerKiloByte; // Same as secondary threads
       
      @@ -251,7 +253,7 @@ void printUsage()
       kJumpedFromUserMainTrampoline,
       };
       
      --extern "C" int main(int argc, char *argv[]);-
      +
       
       static void __attribute__((noinline, noreturn)) user_main_trampoline()
       {
      @@ -270,7 +272,7 @@ static void __attribute__((noinline, noreturn)) user_main_trampoline()
       qFatal("Could not convert argv[%d] to C string", i);
       }
       
      -- int exitCode = main(argc, argv);-
      + int exitCode = *main_ptr*(argc, argv);
       delete[] argv;
       
       logActivity.applicationDidFinishLaunching.enter();
      

       

      1. Add plugins/platforms/libqios.dylib to linked libraries and modify your project entrypoint to be main_wrapper() instead of main() in build options:

      -Wl,-e,_main_wrapper

       

      1. In your main.cpp add this simple code, which will only work when building for iOS:

       

      int main(int argc, char **argv) {
       Application app(argc, argv);
       return app.exec();
      }
      
      <p></p>
      
      #if TARGET_OS_IPHONE
      *extern "C" int qt_main_wrapper(int argc, char *argv[], int (*f)(int, char **));* //this function is inside libqios.dylib
      extern "C" int main_wrapper(int argc, char **argv) { //this is the entry point
      *qt_main_wrapper*(argc, argv, *main*);//once finished, it will call into the real "main()" above
      }
      #endif
      

       

      How this works:

      • Your app starts executing in main_wrapper().

      • main_wrapper() calls into libqios.dylib's qt_main_wrapper() and passes function pointer to the real main() function.

      • qt_main_wrapper() executes some iOS custom ObjectiveC glue code and waits until 
        applicationDidFinishLaunching notification is received
      • Once applicationDidFinishLaunching is received (your app becomes operational), libqios.dylib executes main() in your app via a function pointer that we passed into qt_main_wrapper().
         

       

      Please add a similar approach or some other solution to allow a purely dynamic build of Qt libraries for iOS.

      Attachments

        1. qqmlimport.patch
          2 kB
        2. qfactoryloader.patch
          2 kB
        3. Archive.zip
          53 kB

        Issue Links

          Activity

            People

              vestbo Tor Arne Vestbø
              dmitriykivilev Dmitriy Kivilev
              Vladimir Minenko Vladimir Minenko
              Votes:
              7 Vote for this issue
              Watchers:
              17 Start watching this issue

              Dates

                Created:
                Updated: