qt5base-lts/mkspecs/macx-ios-clang/features/qt.prf

76 lines
3.5 KiB
Plaintext
Raw Normal View History

equals(TEMPLATE, app):contains(QT, gui(-private)?) {
!macx-xcode: \
error("Linking the iOS platform plugin requires bulding through Xcode")
LIBS *= -L$$[QT_INSTALL_PLUGINS/get]/platforms
lib_name = qios
lib_path_and_base = $$[QT_INSTALL_PLUGINS/get]/platforms/lib$${lib_name}$$qtPlatformTargetSuffix()
LIBS += -l$${lib_name}$$qtPlatformTargetSuffix() $$fromfile($${lib_path_and_base}.prl, QMAKE_PRL_LIBS)
# By marking qt_registerPlatformPlugin as undefined, we ensure that
# the plugin.o translation unit is considered for inclusion in
# the final binary, which in turn ensures that the plugin's
# static initializer is included and run.
QMAKE_LFLAGS += -u _qt_registerPlatformPlugin
# We do link and dependency resolution for the platform plugin
# manually, since we know we always need the plugin, so we don't
# need to generate an import for it.
CONFIG -= import_qpa_plugin
iOS: Change main-wrapper logic to not require changing the user's main Instead of using a define to rename the user's main() function during compilation, we leave the user code alone, and inject our wrapper one step earlier in the process, at the application entry point 'start'. This entry point is provided by crt1.o, which is normally linked into the application automatically. The start() function sets up some state and then calls main(), but we change the start() function to instead call our main wrapper. Instead of shipping our own crt1 binary/sources, we make a copy of the appropriate crt1.o at build time, and modify its symbol table in place. This is unproblematic as long as we keep the same length for the wrapper function name, as the symbol names are just entries in the global string table of the object file. The result is that for the regular Qt use-case the user won't see any changes to their main function, and we have more control over the startup sequence. For the hybrid use-case, we no longer rely on the fragile solution of having our back-up 'main' symbol in a single translation unit, which would break eg with --load_all, and we don't need to provide a dummy 'qt_user_main' symbol. OSX 10.8 and iOS 6.0 introduced a new load command called LC_MAIN, which places the state setup in the shared dyld, and then just calls main() directly. Once we bump the minimum deployment target to iOS 6.0 we can start using this loader instead of LC_UNIXTHREAD, but for now we force the classic loader using the -no_new_main flag. There's also a bug in the ld64 linker provided by the current Xcode toolchains that results in the -e linker flag (to set the entry point) having no effect, but hopefully this bug has been fixed (or Apple has switched to the LLVM lld linker) by the time we bump our deployment target. Change-Id: Ie0ba869c13ddc5277dc95c539aebaeb60e949dc2 Reviewed-by: Tor Arne Vestbø <tor.arne.vestbo@digia.com>
2013-09-06 21:16:28 +00:00
!no_main_wrapper {
# Instead of messing with the user's main function we go the other
# way and change the application entry point to call our main wrapper.
# This entry point is the 'start' symbol, provided by crt1.o, so we
# make a copy of the file and rename the '_main' unresolved symbol
# to our wrapper function, '_qtmn', injecting ourselves into the app
# startup. Once Apple starts shipping the LLVM linker (lld) we may
# get rid of this step completely and just pass -e _qtmn to the
# linker, taking advantage of the new LC_MAIN load command.
# We know that iOS 3.1 and up uses crt1.3.1.o (technically not
iOS: Change main-wrapper logic to not require changing the user's main Instead of using a define to rename the user's main() function during compilation, we leave the user code alone, and inject our wrapper one step earlier in the process, at the application entry point 'start'. This entry point is provided by crt1.o, which is normally linked into the application automatically. The start() function sets up some state and then calls main(), but we change the start() function to instead call our main wrapper. Instead of shipping our own crt1 binary/sources, we make a copy of the appropriate crt1.o at build time, and modify its symbol table in place. This is unproblematic as long as we keep the same length for the wrapper function name, as the symbol names are just entries in the global string table of the object file. The result is that for the regular Qt use-case the user won't see any changes to their main function, and we have more control over the startup sequence. For the hybrid use-case, we no longer rely on the fragile solution of having our back-up 'main' symbol in a single translation unit, which would break eg with --load_all, and we don't need to provide a dummy 'qt_user_main' symbol. OSX 10.8 and iOS 6.0 introduced a new load command called LC_MAIN, which places the state setup in the shared dyld, and then just calls main() directly. Once we bump the minimum deployment target to iOS 6.0 we can start using this loader instead of LC_UNIXTHREAD, but for now we force the classic loader using the -no_new_main flag. There's also a bug in the ld64 linker provided by the current Xcode toolchains that results in the -e linker flag (to set the entry point) having no effect, but hopefully this bug has been fixed (or Apple has switched to the LLVM lld linker) by the time we bump our deployment target. Change-Id: Ie0ba869c13ddc5277dc95c539aebaeb60e949dc2 Reviewed-by: Tor Arne Vestbø <tor.arne.vestbo@digia.com>
2013-09-06 21:16:28 +00:00
# true for simulator, but the SDK has a symlink to the correct file).
original_crt_path = "$(SDK_DIR)/usr/lib/crt1.3.1.o"
iOS: Change main-wrapper logic to not require changing the user's main Instead of using a define to rename the user's main() function during compilation, we leave the user code alone, and inject our wrapper one step earlier in the process, at the application entry point 'start'. This entry point is provided by crt1.o, which is normally linked into the application automatically. The start() function sets up some state and then calls main(), but we change the start() function to instead call our main wrapper. Instead of shipping our own crt1 binary/sources, we make a copy of the appropriate crt1.o at build time, and modify its symbol table in place. This is unproblematic as long as we keep the same length for the wrapper function name, as the symbol names are just entries in the global string table of the object file. The result is that for the regular Qt use-case the user won't see any changes to their main function, and we have more control over the startup sequence. For the hybrid use-case, we no longer rely on the fragile solution of having our back-up 'main' symbol in a single translation unit, which would break eg with --load_all, and we don't need to provide a dummy 'qt_user_main' symbol. OSX 10.8 and iOS 6.0 introduced a new load command called LC_MAIN, which places the state setup in the shared dyld, and then just calls main() directly. Once we bump the minimum deployment target to iOS 6.0 we can start using this loader instead of LC_UNIXTHREAD, but for now we force the classic loader using the -no_new_main flag. There's also a bug in the ld64 linker provided by the current Xcode toolchains that results in the -e linker flag (to set the entry point) having no effect, but hopefully this bug has been fixed (or Apple has switched to the LLVM lld linker) by the time we bump our deployment target. Change-Id: Ie0ba869c13ddc5277dc95c539aebaeb60e949dc2 Reviewed-by: Tor Arne Vestbø <tor.arne.vestbo@digia.com>
2013-09-06 21:16:28 +00:00
xcode_objects_path = "$(OBJECT_FILE_DIR_$(CURRENT_VARIANT))/$(CURRENT_ARCH)"
custom_crt_filename = "crt1_qt.o"
custom_crt_path = "$$xcode_objects_path/$$custom_crt_filename"
EOC = $$escape_expand(\\n\\t)
create_custom_crt.commands = \
# Copy original crt1 to build directory
"$$QMAKE_COPY_FILE $$original_crt_path $$custom_crt_path $$EOC" \
# And rename all occurrences of _main to _qtmn
"strings -t d - $${custom_crt_path}" \
"| sed -n 's/^\\([0-9]\\{1,\\}\\) _main\$\$/\1/p'" \
"| while read offset; do" \
"printf '_qtmn'" \
"| dd of=$${custom_crt_path} bs=1 seek=\$\$offset conv=notrunc >/dev/null 2>&1" \
"; done"
create_custom_crt.depends = $$original_crt_path
create_custom_crt.target = $$custom_crt_path
preprocess.depends = create_custom_crt
QMAKE_EXTRA_TARGETS += create_custom_crt preprocess
clean_custom_crt.commands = "$$QMAKE_DEL_FILE $$custom_crt_path"
preprocess_clean.depends += clean_custom_crt
QMAKE_EXTRA_TARGETS += clean_custom_crt preprocess_clean
# Prevent usage of new LC_MAIN load command, which skips start/crt1
# and calls main from the loader. We rely on injecting into start.
QMAKE_LFLAGS += -Wl,-no_new_main
# Explicitly link against our modified crt1 object
QMAKE_LFLAGS += -nostartfiles -l$${custom_crt_filename}
# Workaround for QMAKE_PBX_LIBPATHS mangling the Xcode variables
lib_search_path.name = LIBRARY_SEARCH_PATHS
lib_search_path.value = $$xcode_objects_path
QMAKE_MAC_XCODE_SETTINGS += lib_search_path
}
}
load(qt)