[Interest] Build Qt from source in 32bit (-platform macx-clang-32)

Nuno Santos nunosantos at imaginando.pt
Thu May 28 18:49:13 CEST 2015


René,

You’re the man! :)

Your tip was right. It is the loader path. I started from the most simple case which is having the lib only linked with QtCore and done the following:

install_name_tool -change ../Frameworks/QtCore.framework/Versions/5/QtCore @loader_path/../Frameworks/QtCore.framework/Versions/5/QtCore audiolab 

The plugin gets loaded by the host successfully.

However, when I tried to add another layer (QtGui), no joy! 

I had already played with install_name_tool a couple of years ago because macdeployqt sometimes doesn’t handle correctly third party lib linking.

When I add the QtGui dependency, audiolab depends on QtCore and QtGui. I used the command above to fix those dependencies.

On QtCore I don’t have to do anything because it only depends on system libs.

But when I get to QtGui, it depends on QtGui itself and on QtCore

I have done the install_name_tool -id to change it accordingly:

QtGui.framework/QtGui:
	@loader_path/../Frameworks/QtGui.framework/Versions/5/QtGui (compatibility version 5.4.0, current version 5.4.1)
	@loader_path/../Frameworks/QtCore.framework/Versions/5/QtCore (compatibility version 5.4.0, current version 5.4.1)

But it didn’t work. I’m not sure when I have to use -id and -change. 

Regards,

Nuno

> On 28 May 2015, at 16:19, René J.V. Bertin <rjvbertin at gmail.com> wrote:
> 
> On Thursday May 28 2015 15:38:41 Nuno Santos wrote:
> 
>> MACKIE:64 nsantos$ file audiolab.vst/Contents/Frameworks/QtCore.framework/Versions/5/QtCore 
>> audiolab.vst/Contents/Frameworks/QtCore.framework/Versions/5/QtCore: Mach-O 64-bit dynamically linked shared library x86_64
> 
> That shows QtCore was not built with the -bundle flag, which is appropriate. Forget my whole ramble about bundles and shared libraries; I overlooked that the failing image is a Qt framework that should be linked as a shared library (and not as a bundle).
> I'm a bit confused as to what the plugin is you're trying to build: is in fact audiolab.vst that plugin? Are you bundling Qt within that plugin bundle, maybe because the host application does not use Qt itself?
> 
> Maybe it's the use of @executable_path that got me confused. As far as I know, this is interpreted relative to the running application, the host loading the plugin, which could be the most straightforward explanation why you get an "image not found" error.
> 
> Cf. https://wincent.com/wiki/@executable_path,_@load_path_and_@rpath .
> 
> 
>>>> I can also observe that the bundle does load, if I don’t run macdeployqt on it. But i’m also sure that it won’t open on another computer without Qt installed on the same path. 
> 
> Yes, that would correspond with my latest idea: without macdeployqt the "rpaths" in your binary aren't changed as if it's an application.
> 
>> Xcode has a template for plugin bundles. 
> 
> I've only used those templates with an older Xcode version, and there you had to do certain things by hand, including setting the "rpath". At least I could never figure out if there was an automatic way to obtain a bundle or framework that could be embedded in an app bundle.
> 
>> macx:{
>>   CONFIG += plugin
>>   QMAKE_LFLAGS_PLUGIN -= -single_module -dynamiclib
>>   QMAKE_LFLAGS_PLUGIN += -bundle
>>   QMAKE_POST_LINK = mv -f $(TARGET) $$TARGET
>>   OTHER_FILES += Info.plist
>> }
>> 
>> This produces a dylib which I rename to target as you can see in the following output:
> 
> Just as a side-note: if you do this with cmake, you get a .so, probably to make it clear the linker won't be able to use it but possibly only to increase the chances that cross-platform code will find the file without having to consider a platform-specific extension.
> 
> 
>> The bundle structure is the following:
>> 
>> target.vst 
>> - PkgInfo 
>> - MacOS
>>  - target (dylib without extension)
>> - Resources
>> 
>> So basically what I do is to manually copy the output lib without the extension inside the MacOS dir.
>> 
>> Then I point the host program to search for plugins in the folder where this is contained, and it gets found.
> 
> Yes, and if "target" instructs the dynamic loader to look for Qt frameworks relative to the host application executable (host.app/Contents/MacOS/host), it won't find them. According to the wiki page above, you'll need to use @loader_path instead of @executable_path
> You'll probably need to do something like
> 
> %> install_name_tool -id @loader_path/../Frameworks/QtGui.framework/Versions/5/QtGui <path-to-bundle-Frameworks-dir>/QtGui.framework/Versions/5/QtGui
> %> install_name_tool -change @executable_path/../Frameworks/QtGui.framework/Versions/5/QtGui @loader_path/../Frameworks/QtGui.framework/Versions/5/QtGui <path-to-audiolab>/audiolab
> 
> Running `otool -L` on QtGui or audiolab will help you hunt down the entries that have to be changed.
> 
> If it's not that, there's still the slight possibility that the image that supposedly isn't found can in fact not be loaded because it depends itself on a shared library that somehow cannot be found. This you can check by doing the equivalent of Linux's ldd command:
> %> otool -L <image-that-cannot-be-found>
> 
> Good luck
> 
> R

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.qt-project.org/pipermail/interest/attachments/20150528/fccfb812/attachment.html>


More information about the Interest mailing list