I'm stuck again with the next issue: starting the PyQt4 app on a pristine mac results in:
Mac OS X Version 10.4.11 (Build 8S165) 2009-07-02 10:06:59 +0200 2009-07-02 10:07:03.260 SystemUIServer[120] lang is:de Workaround Bonjour: Unknown error: 0 Traceback (most recent call last): File "<string>", line 34, in <module> File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 480, in importHook File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 498, in doimport File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 300, in getmod File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/archive.py", line 468, in getmod File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 109, in getmod ImportError: dlopen(/Applications/CReport.app/Contents/MacOS/PyQt4.QtCore.so, 2): Library not loaded: QtCore.framework/Versions/4/QtCore Referenced from: /Applications/CReport.app/Contents/MacOS/PyQt4.QtCore.so Reason: image not found
Apart from the devel path leaking into the app, it obviously cannot locate the QtCore library. BTW, there where issues with BUNDLE(), I examine later. For now, the manually created bundle with .app/Contents/MacOS containing everything from the one-dir run should be sufficient. Here the MacOS folder content:
Looks like the PyQt modules try to access QtCore.framework/Versions/4 which seem to be missing:
$ otool -L CReport.app/Contents/MacOS/PyQt4.Qt* CReport.app/Contents/MacOS/PyQt4.QtCore.so: QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) /usr/lib/libz.1.dylib (compatibility version 1.0.0, current version 1.2.3) /usr/lib/libSystem.B.dylib (compatibility version 1.0.0, current version 111.1.4) /System/Library/Frameworks/ApplicationServices.framework/Versions/A/Applica tionServices (compatibility version 1.0.0, current version 34.0.0) /usr/lib/libstdc++.6.dylib (compatibility version 7.0.0, current version 7.4.0) /usr/lib/libgcc_s.1.dylib (compatibility version 1.0.0, current version 1.0.0) CReport.app/Contents/MacOS/PyQt4.QtGui.so: QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) /System/Library/Frameworks/Carbon.framework/Versions/A/Carbon (compatibility version 2.0.0, current version 136.0.0) /System/Library/Frameworks/AppKit.framework/Versions/C/AppKit (compatibility version 45.0.0, current version 949.46.0) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) /usr/lib/libz.1.dylib (compatibility version 1.0.0, current version 1.2.3) /usr/lib/libSystem.B.dylib (compatibility version 1.0.0, current version 111.1.4) /usr/lib/libstdc++.6.dylib (compatibility version 7.0.0, current version 7.4.0) /usr/lib/libgcc_s.1.dylib (compatibility version 1.0.0, current version 1.0.0)
Shouldn't this work out of the box? I would very much like to keep the original Qt build, I'm using here. Needless to say, running it with Qt installed, works fine. (There seem to be similar issues with the qt4_plugins location which gets picked up from the systems Qt installation, rather then those incuded in the package.
Current packages installed on the developer machine: xcode313_2736_developerdvd.dmg python-2.6.2-macosx2009-04-16.dmg qt-sdk-mac-opensource-2009.03.dmg sip-4.8.1.tar.gz PyQt-mac-gpl-4.5.1.tar.gz (with minor Configure.py patch for Qt 4.5.2 compatibility) http://svn.pyinstaller.org/trunk:685
> I'm stuck again with the next issue: starting the PyQt4 app on a pristine > mac results in:
> Mac OS X Version 10.4.11 (Build 8S165) > 2009-07-02 10:06:59 +0200 > 2009-07-02 10:07:03.260 SystemUIServer[120] lang is:de > Workaround Bonjour: Unknown error: 0 > Traceback (most recent call last): > File "<string>", line 34, in <module> > File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", > line 480, in importHook File > "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 498, > in doimport File > "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 300, > in getmod File > "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/archive.py", line > 468, in getmod File > "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 109, > in getmod ImportError: > dlopen(/Applications/CReport.app/Contents/MacOS/PyQt4.QtCore.so, 2): > Library not loaded: QtCore.framework/Versions/4/QtCore Referenced from: > /Applications/CReport.app/Contents/MacOS/PyQt4.QtCore.so Reason: image > not found
> Apart from the devel path leaking into the app, it obviously cannot > locate the QtCore library. BTW, there where issues with BUNDLE(), I > examine later. For now, the manually created bundle with > .app/Contents/MacOS containing everything from the one-dir run should be > sufficient. Here the MacOS folder content:
> Looks like the PyQt modules try to access QtCore.framework/Versions/4 > which seem to be missing:
> $ otool -L CReport.app/Contents/MacOS/PyQt4.Qt* > CReport.app/Contents/MacOS/PyQt4.QtCore.so: > QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, > current version 4.5.2) /usr/lib/libz.1.dylib (compatibility version > 1.0.0, current version 1.2.3) /usr/lib/libSystem.B.dylib (compatibility > version 1.0.0, current version 111.1.4) > /System/Library/Frameworks/ApplicationServices.framework/Versions/A/Appli >cationServices (compatibility version 1.0.0, current version 34.0.0) > /usr/lib/libstdc++.6.dylib (compatibility version 7.0.0, current > version 7.4.0) /usr/lib/libgcc_s.1.dylib (compatibility version 1.0.0, > current version 1.0.0) CReport.app/Contents/MacOS/PyQt4.QtGui.so: > QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, > current version 4.5.2) > /System/Library/Frameworks/Carbon.framework/Versions/A/Carbon > (compatibility version 2.0.0, current version 136.0.0) > /System/Library/Frameworks/AppKit.framework/Versions/C/AppKit > (compatibility version 45.0.0, current version 949.46.0) > QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current > version 4.5.2) /usr/lib/libz.1.dylib (compatibility version 1.0.0, > current version 1.2.3) /usr/lib/libSystem.B.dylib (compatibility version > 1.0.0, current version 111.1.4) /usr/lib/libstdc++.6.dylib (compatibility > version 7.0.0, current version 7.4.0) /usr/lib/libgcc_s.1.dylib > (compatibility version 1.0.0, current version 1.0.0)
> Shouldn't this work out of the box? I would very much like to keep the > original Qt build, I'm using here. Needless to say, running it with > Qt installed, works fine. (There seem to be similar issues with the > qt4_plugins location which gets picked up from the systems Qt > installation, rather then those incuded in the package.
> Current packages installed on the developer machine: > xcode313_2736_developerdvd.dmg > python-2.6.2-macosx2009-04-16.dmg > qt-sdk-mac-opensource-2009.03.dmg > sip-4.8.1.tar.gz > PyQt-mac-gpl-4.5.1.tar.gz (with minor Configure.py patch for Qt 4.5.2 > compatibility) http://svn.pyinstaller.org/trunk:685
> Am Donnerstag, 2. Juli 2009 schrieb Hans-Peter Jansen: [...]
> > $ otool -L CReport.app/Contents/MacOS/PyQt4.Qt* > > CReport.app/Contents/MacOS/PyQt4.QtCore.so: > > QtCore.framework/Versions/4/QtCore (compatibility version > > 4.5.0, current version 4.5.2) /usr/lib/libz.1.dylib (compatibility > > version 1.0.0, current version 1.2.3) /usr/lib/libSystem.B.dylib > > (compatibility version 1.0.0, current version 111.1.4) > > /System/Library/Frameworks/ApplicationServices.framework/Versions/A/App > >li cationServices (compatibility version 1.0.0, current version 34.0.0) > > /usr/lib/libstdc++.6.dylib (compatibility version 7.0.0, current > > version 7.4.0) /usr/lib/libgcc_s.1.dylib (compatibility version 1.0.0, > > current version 1.0.0) CReport.app/Contents/MacOS/PyQt4.QtGui.so: > > QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current > > version 4.5.2) > > /System/Library/Frameworks/Carbon.framework/Versions/A/Carbon > > (compatibility version 2.0.0, current version 136.0.0) > > /System/Library/Frameworks/AppKit.framework/Versions/C/AppKit > > (compatibility version 45.0.0, current version 949.46.0) > > QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, > > current version 4.5.2) /usr/lib/libz.1.dylib (compatibility version > > 1.0.0, current version 1.2.3) /usr/lib/libSystem.B.dylib (compatibility > > version 1.0.0, current version 111.1.4) /usr/lib/libstdc++.6.dylib > > (compatibility version 7.0.0, current version 7.4.0) > > /usr/lib/libgcc_s.1.dylib (compatibility version 1.0.0, current version > > 1.0.0)
> > Shouldn't this work out of the box? I would very much like to keep the > > original Qt build, I'm using here. Needless to say, running it with > > Qt installed, works fine. (There seem to be similar issues with the > > qt4_plugins location which gets picked up from the systems Qt > > installation, rather then those incuded in the package.
> > Current packages installed on the developer machine: > > xcode313_2736_developerdvd.dmg > > python-2.6.2-macosx2009-04-16.dmg > > qt-sdk-mac-opensource-2009.03.dmg > > sip-4.8.1.tar.gz > > PyQt-mac-gpl-4.5.1.tar.gz (with minor Configure.py patch for Qt 4.5.2 > > compatibility) http://svn.pyinstaller.org/trunk:685
> Seems to me, that there's quite a bit of way to go before this all is > usable painlessly.
Giovanni, if I add code for Qt library relocation/inclusion for PyInstaller, could you please briefly outline the way, you would do it (in order that you can accept these patches later?
> Shouldn't this work out of the box? I would very much like to keep the > original Qt build, I'm using here. Needless to say, running it with > Qt installed, works fine.
Yes, it should work out of the box, and I have sucessfully managed to ship PyQt applications on Mac.
It might be related to the fact that PyInstaller seems not to set DYLD_LIBRARY_PATH correctly in one-dir mode.
Does it work in one-file mode? If so, it's should be easy to fix. -- Giovanni Bajo Develer S.r.l. http://www.develer.com
Am Donnerstag, 2. Juli 2009 schrieb Giovanni Bajo:
> On 7/2/2009 11:23 AM, Hans-Peter Jansen wrote: > > Shouldn't this work out of the box? I would very much like to keep the > > original Qt build, I'm using here. Needless to say, running it with > > Qt installed, works fine.
> Yes, it should work out of the box, and I have sucessfully managed to > ship PyQt applications on Mac.
> It might be related to the fact that PyInstaller seems not to set > DYLD_LIBRARY_PATH correctly in one-dir mode.
Hmm, given that the libs are missing, how could setting a environment variable fix that problem?
> Does it work in one-file mode? If so, it's should be easy to fix.
No, it doesn't, but since the analyse part is the same, it cannot.
Did you really shipped apps, based on a current Qt framework build, and it worked out of the box (without Qt installed on the target systems)?!?
# check, if something is still missing otool -L ../MacOS/PyQt4.Qt*.so QtCore.framework/QtCore QtGui.framework/QtGui
You see, the whole mess is asking for automatic treatment. What I'm thinking about, is getting rid of the Framework junk, and simply throw the lib files QtCore, QtGui, etc into "the" dir (renaming them to Qt*.so), and do the adjustments as outlined above, but I haven't tried this yet.
I think, this deserves a mac related option (one may don't want to ship Qt), but by default the libs should be included. Using qt4_plugins may deserve another option, since they need the same treatment as above, and on that way pull nearly the full distribution into the bundle. Thus I may decide to do without them, and spare a lot of space. BTW, do you know, what codecs are shipped in libqtwcodecs.dylib? They can't be essential, since my simple app works without them at least (due to missing "the" treatment ATM).
On gio, 2009-07-02 at 21:56 +0200, Hans-Peter Jansen wrote:
> Am Donnerstag, 2. Juli 2009 schrieb Giovanni Bajo: > > On 7/2/2009 11:23 AM, Hans-Peter Jansen wrote: > > > Shouldn't this work out of the box? I would very much like to keep the > > > original Qt build, I'm using here. Needless to say, running it with > > > Qt installed, works fine.
> > Yes, it should work out of the box, and I have sucessfully managed to > > ship PyQt applications on Mac.
> > It might be related to the fact that PyInstaller seems not to set > > DYLD_LIBRARY_PATH correctly in one-dir mode.
> Hmm, given that the libs are missing, how could setting a environment > variable fix that problem?
Sorry, I had misread your original mail.
> > Does it work in one-file mode? If so, it's should be easy to fix.
> No, it doesn't, but since the analyse part is the same, it cannot.
> Did you really shipped apps, based on a current Qt framework build, and it > worked out of the box (without Qt installed on the target systems)?!?
Yes. I'm not 100% sure my deployment Mac has the standard Qt framework though; I'll have to check.
I still can't see what it is going on. mf.py (which is the dependency analyzer) should be able to find the Qt libraries from the PyQt4 ones. What happens if you run "bindepend.py PyQt4.QtCore4.so"? Does it list Qt dependencies? Under what path?
> # check, if something is still missing > otool -L ../MacOS/PyQt4.Qt*.so QtCore.framework/QtCore QtGui.framework/QtGui
> You see, the whole mess is asking for automatic treatment. What I'm thinking > about, is getting rid of the Framework junk, and simply throw the lib files > QtCore, QtGui, etc into "the" dir (renaming them to Qt*.so), and do the > adjustments as outlined above, but I haven't tried this yet.
Yes it would be better to just put everything inside the output directory, like we do on other platforms (unless dyld makes this really impossible -- which I hope it does not).
The install_name_tool trick shouldn't be necessary: I used to do it automatically in PyInstaller, but it turned out to have compatibility problems across different Mac OSX versions (I don't recall details) and setting DYLD_LIBRARY_PATH instead was just as effective.
You don't need to rename Qt libraries to ".so". If I recall correctly, they can stay as-is. Just try copying them within the output directory and see what happens (and set DYLD_LIBRARY_PATH to point to that directory as well).
> I think, this deserves a mac related option (one may don't want to ship > Qt), but by default the libs should be included. Using qt4_plugins may > deserve another option, since they need the same treatment as above, and > on that way pull nearly the full distribution into the bundle.
This is a totally different topic, as PyInstaller treats qt4_plugins mostly as data files. We'll have to find out why hook-PyQt4.Qt*.py don't find the Qt4 plugins directory.
> Thus I may > decide to do without them, and spare a lot of space. BTW, do you know, > what codecs are shipped in libqtwcodecs.dylib? They can't be essential, > since my simple app works without them at least (due to missing "the" > treatment ATM).
> On gio, 2009-07-02 at 21:56 +0200, Hans-Peter Jansen wrote: > > Am Donnerstag, 2. Juli 2009 schrieb Giovanni Bajo: > > > On 7/2/2009 11:23 AM, Hans-Peter Jansen wrote: > > > > Shouldn't this work out of the box? I would very much like to keep > > > > the original Qt build, I'm using here. Needless to say, running it > > > > with Qt installed, works fine.
> > > Yes, it should work out of the box, and I have sucessfully managed to > > > ship PyQt applications on Mac.
> > > It might be related to the fact that PyInstaller seems not to set > > > DYLD_LIBRARY_PATH correctly in one-dir mode.
> > Hmm, given that the libs are missing, how could setting a environment > > variable fix that problem?
> Sorry, I had misread your original mail.
Excuse me, I don't wanted to sound rude. I tend to be explicite sometimes..
> > > Does it work in one-file mode? If so, it's should be easy to fix.
> > No, it doesn't, but since the analyse part is the same, it cannot.
> > Did you really shipped apps, based on a current Qt framework build, and > > it worked out of the box (without Qt installed on the target > > systems)?!?
> Yes. I'm not 100% sure my deployment Mac has the standard Qt framework > though; I'll have to check.
> I still can't see what it is going on. mf.py (which is the dependency > analyzer) should be able to find the Qt libraries from the PyQt4 ones. > What happens if you run "bindepend.py PyQt4.QtCore4.so"? Does it list Qt > dependencies? Under what path?
> > # check, if something is still missing > > otool -L ../MacOS/PyQt4.Qt*.so QtCore.framework/QtCore > > QtGui.framework/QtGui
> > You see, the whole mess is asking for automatic treatment. What I'm > > thinking about, is getting rid of the Framework junk, and simply throw > > the lib files QtCore, QtGui, etc into "the" dir (renaming them to > > Qt*.so), and do the adjustments as outlined above, but I haven't tried > > this yet.
> Yes it would be better to just put everything inside the output > directory, like we do on other platforms (unless dyld makes this really > impossible -- which I hope it does not).
> The install_name_tool trick shouldn't be necessary: I used to do it > automatically in PyInstaller, but it turned out to have compatibility > problems across different Mac OSX versions (I don't recall details) and > setting DYLD_LIBRARY_PATH instead was just as effective.
Traceback (most recent call last): File "<string>", line 36, in <module> File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 480, in importHook File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 498, in doimport File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 300, in getmod File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/archive.py", line 468, in getmod File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 109, in getmod ImportError: dlopen(/Applications/CReport.app/Contents/MacOS/PyQt4.QtCore.so, 2): Library not loaded: QtCore.framework/Versions/4/QtCore Referenced from: /Applications/CReport.app/Contents/MacOS/PyQt4.QtCore.so Reason: image not found
I tried to find the right spot for adding it, but failed. source/linux/main.s looks to me, like it should appear (as long as workpath is not empty).
> You don't need to rename Qt libraries to ".so". If I recall correctly, > they can stay as-is. Just try copying them within the output directory > and see what happens (and set DYLD_LIBRARY_PATH to point to that > directory as well).
Could you give me the hint, where DYLD_LIBRARY_PATH is missing, and I'm testing it right away.
> > I think, this deserves a mac related option (one may don't want to ship > > Qt), but by default the libs should be included. Using qt4_plugins may > > deserve another option, since they need the same treatment as above, > > and on that way pull nearly the full distribution into the bundle.
> This is a totally different topic, as PyInstaller treats qt4_plugins > mostly as data files. We'll have to find out why hook-PyQt4.Qt*.py don't > find the Qt4 plugins directory.
It looks like QT_PLUGIN_PATH is set correctly, and they also appear altogether, but those plugins bind with nearly all Qt libs in existence, and this dependancy is not handled correctly, yet.
$ find . -name \*.dylib -exec otool -L {} \; | grep -i qt ./accessible/libqtaccessiblecompatwidgets.dylib: libqtaccessiblecompatwidgets.dylib (compatibility version 0.0.0, current version 0.0.0) Qt3Support.framework/Versions/4/Qt3Support (compatibility version 4.5.0, current version 4.5.2) QtSql.framework/Versions/4/QtSql (compatibility version 4.5.0, current version 4.5.2) QtXml.framework/Versions/4/QtXml (compatibility version 4.5.0, current version 4.5.2) QtNetwork.framework/Versions/4/QtNetwork (compatibility version 4.5.0, current version 4.5.2) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./accessible/libqtaccessiblewidgets.dylib: libqtaccessiblewidgets.dylib (compatibility version 0.0.0, current version 0.0.0) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./codecs/libqtwcodecs.dylib: libqtwcodecs.dylib (compatibility version 0.0.0, current version 0.0.0) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) QtSvg.framework/Versions/4/QtSvg (compatibility version 4.5.0, current version 4.5.2) QtXml.framework/Versions/4/QtXml (compatibility version 4.5.0, current version 4.5.2) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) QtSvg.framework/Versions/4/QtSvg (compatibility version 4.5.0, current
...
Am Freitag, 3. Juli 2009 schrieb Hans-Peter Jansen:
> It looks like QT_PLUGIN_PATH is set correctly, and they also appear > altogether, but those plugins bind with nearly all Qt libs in existence, > and this dependancy is not handled correctly, yet.
Oops, not complete:
$ find . -name \*.dylib -exec otool -L {} \; | egrep -i 'qt|libq' ./accessible/libqtaccessiblecompatwidgets.dylib: libqtaccessiblecompatwidgets.dylib (compatibility version 0.0.0, current version 0.0.0) Qt3Support.framework/Versions/4/Qt3Support (compatibility version 4.5.0, current version 4.5.2) QtSql.framework/Versions/4/QtSql (compatibility version 4.5.0, current version 4.5.2) QtXml.framework/Versions/4/QtXml (compatibility version 4.5.0, current version 4.5.2) QtNetwork.framework/Versions/4/QtNetwork (compatibility version 4.5.0, current version 4.5.2) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./accessible/libqtaccessiblewidgets.dylib: libqtaccessiblewidgets.dylib (compatibility version 0.0.0, current version 0.0.0) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./codecs/libqcncodecs.dylib: libqcncodecs.dylib (compatibility version 0.0.0, current version 0.0.0) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./codecs/libqjpcodecs.dylib: libqjpcodecs.dylib (compatibility version 0.0.0, current version 0.0.0) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./codecs/libqkrcodecs.dylib: libqkrcodecs.dylib (compatibility version 0.0.0, current version 0.0.0) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./codecs/libqtwcodecs.dylib: libqtwcodecs.dylib (compatibility version 0.0.0, current version 0.0.0) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./iconengines/libqsvgicon.dylib: libqsvgicon.dylib (compatibility version 0.0.0, current version 0.0.0) QtSvg.framework/Versions/4/QtSvg (compatibility version 4.5.0, current version 4.5.2) QtXml.framework/Versions/4/QtXml (compatibility version 4.5.0, current version 4.5.2) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./imageformats/libqgif.dylib: libqgif.dylib (compatibility version 0.0.0, current version 0.0.0) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./imageformats/libqico.dylib: libqico.dylib (compatibility version 0.0.0, current version 0.0.0) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./imageformats/libqjpeg.dylib: libqjpeg.dylib (compatibility version 0.0.0, current version 0.0.0) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./imageformats/libqmng.dylib: libqmng.dylib (compatibility version 0.0.0, current version 0.0.0) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./imageformats/libqsvg.dylib: libqsvg.dylib (compatibility version 0.0.0, current version 0.0.0) QtSvg.framework/Versions/4/QtSvg (compatibility version 4.5.0, current version 4.5.2) QtXml.framework/Versions/4/QtXml (compatibility version 4.5.0, current version 4.5.2) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2) ./imageformats/libqtiff.dylib: libqtiff.dylib (compatibility version 0.0.0, current version 0.0.0) QtGui.framework/Versions/4/QtGui (compatibility version 4.5.0, current version 4.5.2) QtCore.framework/Versions/4/QtCore (compatibility version 4.5.0, current version 4.5.2)
Am Freitag, 3. Juli 2009 schrieb Hans-Peter Jansen:
> > Yes it would be better to just put everything inside the output > > directory, like we do on other platforms (unless dyld makes this really > > impossible -- which I hope it does not).
No, at least with lib relocation via install_name_tool all is well. Just tested. I guess, that setting DYLD_LIBRARY_PATH will be fine, too. Will test as soon as you give me the hint on how to get this going.
And now for something completely different: why get checkable group boxes rendered different between Mac OS-X 10.4 and 10.5 and why is the font kerning damaged on the latter.. Oh well. Let's see what the trolls say!
> Am Freitag, 3. Juli 2009 schrieb Giovanni Bajo: >> On gio, 2009-07-02 at 21:56 +0200, Hans-Peter Jansen wrote: >>> Am Donnerstag, 2. Juli 2009 schrieb Giovanni Bajo: >>>> On 7/2/2009 11:23 AM, Hans-Peter Jansen wrote: >>>>> Shouldn't this work out of the box? I would very much like to keep >>>>> the original Qt build, I'm using here. Needless to say, running it >>>>> with Qt installed, works fine. >>>> Yes, it should work out of the box, and I have sucessfully managed to >>>> ship PyQt applications on Mac.
>>>> It might be related to the fact that PyInstaller seems not to set >>>> DYLD_LIBRARY_PATH correctly in one-dir mode. >>> Hmm, given that the libs are missing, how could setting a environment >>> variable fix that problem? >> Sorry, I had misread your original mail.
> Excuse me, I don't wanted to sound rude. I tend to be explicite sometimes..
>>>> Does it work in one-file mode? If so, it's should be easy to fix. >>> No, it doesn't, but since the analyse part is the same, it cannot.
>>> Did you really shipped apps, based on a current Qt framework build, and >>> it worked out of the box (without Qt installed on the target >>> systems)?!? >> Yes. I'm not 100% sure my deployment Mac has the standard Qt framework >> though; I'll have to check.
>> I still can't see what it is going on. mf.py (which is the dependency >> analyzer) should be able to find the Qt libraries from the PyQt4 ones. >> What happens if you run "bindepend.py PyQt4.QtCore4.so"? Does it list Qt >> dependencies? Under what path?
OK, this requires some Mac Guru to tell us how dyld resolves the dependencies at runtime. I thought otool -L always output absolute paths, but if that's not the case, how are we supposed to find out the absolute paths?
I don't have a Mac right now. Maybe someone can chime in?
>>> # check, if something is still missing >>> otool -L ../MacOS/PyQt4.Qt*.so QtCore.framework/QtCore >>> QtGui.framework/QtGui
>>> You see, the whole mess is asking for automatic treatment. What I'm >>> thinking about, is getting rid of the Framework junk, and simply throw >>> the lib files QtCore, QtGui, etc into "the" dir (renaming them to >>> Qt*.so), and do the adjustments as outlined above, but I haven't tried >>> this yet. >> Yes it would be better to just put everything inside the output >> directory, like we do on other platforms (unless dyld makes this really >> impossible -- which I hope it does not).
>> The install_name_tool trick shouldn't be necessary: I used to do it >> automatically in PyInstaller, but it turned out to have compatibility >> problems across different Mac OSX versions (I don't recall details) and >> setting DYLD_LIBRARY_PATH instead was just as effective.
> Traceback (most recent call last): > File "<string>", line 36, in <module> > File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 480, in importHook > File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 498, in doimport > File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 300, in getmod > File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/archive.py", line 468, in getmod > File "/Users/hp/Desktop/PyQt-Devel/creport/tools/pyinstaller/iu.py", line 109, in getmod > ImportError: dlopen(/Applications/CReport.app/Contents/MacOS/PyQt4.QtCore.so, 2): > Library not loaded: QtCore.framework/Versions/4/QtCore > Referenced from: /Applications/CReport.app/Contents/MacOS/PyQt4.QtCore.so > Reason: image not found
> I tried to find the right spot for adding it, but failed. source/linux/main.s > looks to me, like it should appear (as long as workpath is not empty).
In one-dir mode, I *believe* that workpath is empty (I'm not sure I fully understand the code in there). Try putting some debug messages in there to debug.
Anyway, to test if it's the right approach, it is of course sufficient to manually set DYLD_LIBRARY_PATH:
$ DYLD_LIBRARY_PATH=`pwd` ./myapp
If this works, at least we know that we don't need to play any install_name_tool game.
>>> I think, this deserves a mac related option (one may don't want to ship >>> Qt), but by default the libs should be included. Using qt4_plugins may >>> deserve another option, since they need the same treatment as above, >>> and on that way pull nearly the full distribution into the bundle. >> This is a totally different topic, as PyInstaller treats qt4_plugins >> mostly as data files. We'll have to find out why hook-PyQt4.Qt*.py don't >> find the Qt4 plugins directory.
> It looks like QT_PLUGIN_PATH is set correctly, and they also appear > altogether, but those plugins bind with nearly all Qt libs in existence, > and this dependancy is not handled correctly, yet.
This should be fixed wherever we fix the PyQt <-> Qt dependency, that is with DYLD_LIBRARY_PATH (hopefully). -- Giovanni Bajo Develer S.r.l. http://www.develer.com
> OK, this requires some Mac Guru to tell us how dyld resolves the > dependencies at runtime. I thought otool -L always output absolute > paths, but if that's not the case, how are we supposed to find out the > absolute paths?
> I don't have a Mac right now. Maybe someone can chime in?
As you know, I'm in no way a Mac Guru, but I'am able to read man pages, which ought to be sufficient in this case:
DYLD_FRAMEWORK_PATH This is a colon separated list of directories that contain frameworks. The dynamic linker searches these directories before it searches for the framework by its install name. It allows you to test new versions of existing frameworks. (A framework is a library install name that ends in the form XXX.framework/Versions/YYY/XXX or XXX.framework/XXX, where XXX and YYY are any name.)
For each framework that a program uses, the dynamic linker looks for the framework in each directory in DYLD_FRAMEWORK_PATH in turn. If it looks in all the directories and can't find the framework, it searches the directories in DYLD_LIBRARY_PATH in turn. If it still can't find the framework, it then searches DYLD_FALLBACK_FRAMEWORK_PATH and DYLD_FALLBACK_LIBRARY_PATH in turn.
Use the -L option to otool(1). to discover the frameworks and shared libraries that the executable is linked against.
DYLD_FALLBACK_FRAMEWORK_PATH This is a colon separated list of directories that contain frameworks. It is used as the default location for frameworks not found in their install path.
By default, it is set to /Library/Frameworks:/Network/Library/Frame- works:/System/Library/Frameworks
Given that info, and leaving DYLD_LIBRARY_PATH, DYLD_FALLBACK_LIBRARY_PATH and DYLD_ROOT_PATH alone, it boils down to this patch:
Index: bindepend.py =================================================================== --- bindepend.py (Revision 59) +++ bindepend.py (Arbeitskopie) @@ -354,6 +354,12 @@ """Find the binary dependencies of PTH.
This implementation is for otool platforms""" + # dyld searches these paths for framework libs + # we ignore DYLD_FALLBACK_LIBRARY_PATH for now (man dyld) + fwpaths = ['/Library/Frameworks', '/Network/Library/Frameworks', '/System/Library/Frameworks'] + for p in reversed(os.environ.get('DYLD_FRAMEWORK_PATH', '').split(':')): + if p: + fwpaths.insert(0, p) rslt = [] for line in os.popen('otool -L "%s"' % pth).readlines(): m = re.search(r"\s+(.*?)\s+\(.*\)", line) @@ -363,6 +369,13 @@ rel_path = lib.replace("@executable_path",".") rel_path = os.path.join(os.path.dirname(pth), rel_path) lib = os.path.abspath(rel_path) + elif not os.path.isabs(lib): + # lookup matching framework path, if relative pathname + for p in fwpaths: + fwlib = os.path.join(p, lib) + if os.path.exists(fwlib): + lib = fwlib + break if os.path.exists(lib): rslt.append(lib) else:
For your convenience, it's also attached.
> In one-dir mode, I *believe* that workpath is empty (I'm not sure I > fully understand the code in there). Try putting some debug messages in > there to debug.
> Anyway, to test if it's the right approach, it is of course sufficient > to manually set DYLD_LIBRARY_PATH:
> $ DYLD_LIBRARY_PATH=`pwd` ./myapp
> If this works, at least we know that we don't need to play any > install_name_tool game.
I'm pretty confident, taht it will, given that all this is documented:
DYLD_LIBRARY_PATH This is a colon separated list of directories that contain libraries. The dynamic linker searches these directories before it searches the default locations for libraries. It allows you to test new versions of existing libraries.
For each library that a program uses, the dynamic linker looks for it in each directory in DYLD_LIBRARY_PATH in turn. If it still can't find the library, it then searches DYLD_FALLBACK_FRAMEWORK_PATH and DYLD_FALLBACK_LIBRARY_PATH in turn.
Use the -L option to otool(1). to discover the frameworks and shared libraries that the executable is linked against.
> >>> I think, this deserves a mac related option (one may don't want to > >>> ship Qt), but by default the libs should be included. Using > >>> qt4_plugins may deserve another option, since they need the same > >>> treatment as above, and on that way pull nearly the full distribution > >>> into the bundle.
> >> This is a totally different topic, as PyInstaller treats qt4_plugins > >> mostly as data files.
That's the culprit!
> >> We'll have to find out why hook-PyQt4.Qt*.py > >> don't find the Qt4 plugins directory.
> > It looks like QT_PLUGIN_PATH is set correctly, and they also appear > > altogether, but those plugins bind with nearly all Qt libs in > > existence, and this dependancy is not handled correctly, yet.
> This should be fixed wherever we fix the PyQt <-> Qt dependency, that is > with DYLD_LIBRARY_PATH (hopefully).
Of course it won't, since you _still_ cannot fix a _missing_ library with playing environmental games ;-) The PyQt <-> Qt dependency is resolved with the attached patch.
You will notice, when this starts to work, because the size of your app will grow considerably (as long as your app doesn't use QtNetwork, QtSql, QtXml, QtSvg, or Qt3Support, yet). They all get pulled with the full qt4_plugins support (see my list), but as you said before, they're handled as data files ATM, which is the root of the problem.
On Fri, 2009-07-03 at 22:59 +0200, Hans-Peter Jansen wrote: > Am Freitag, 3. Juli 2009 schrieb Giovanni Bajo: > > On 7/3/2009 3:42 PM, Hans-Peter Jansen wrote: > Given that info, and leaving DYLD_LIBRARY_PATH, DYLD_FALLBACK_LIBRARY_PATH > and DYLD_ROOT_PATH alone, it boils down to this patch:
> This implementation is for otool platforms""" > + # dyld searches these paths for framework libs > + # we ignore DYLD_FALLBACK_LIBRARY_PATH for now (man dyld) > + fwpaths = ['/Library/Frameworks', '/Network/Library/Frameworks', '/System/Library/Frameworks'] > + for p in reversed(os.environ.get('DYLD_FRAMEWORK_PATH', '').split(':')): > + if p: > + fwpaths.insert(0, p) > rslt = [] > for line in os.popen('otool -L "%s"' % pth).readlines(): > m = re.search(r"\s+(.*?)\s+\(.*\)", line) > @@ -363,6 +369,13 @@ > rel_path = lib.replace("@executable_path",".") > rel_path = os.path.join(os.path.dirname(pth), rel_path) > lib = os.path.abspath(rel_path) > + elif not os.path.isabs(lib): > + # lookup matching framework path, if relative pathname > + for p in fwpaths: > + fwlib = os.path.join(p, lib) > + if os.path.exists(fwlib): > + lib = fwlib > + break > if os.path.exists(lib): > rslt.append(lib) > else:
> For your convenience, it's also attached.
Thanks. I have committed this patch since it seems correct, given the manpage.
I have also fixed the {DY}LD_LIBRARY_PATH issue in one-dir mode. Now one-dir mode builds correctly set the environment variable and fork+exec to make sure it is honored (exactly what one-file builds do).
> > >> We'll have to find out why hook-PyQt4.Qt*.py > > >> don't find the Qt4 plugins directory.
> > > It looks like QT_PLUGIN_PATH is set correctly, and they also appear > > > altogether, but those plugins bind with nearly all Qt libs in > > > existence, and this dependancy is not handled correctly, yet.
> > This should be fixed wherever we fix the PyQt <-> Qt dependency, that is > > with DYLD_LIBRARY_PATH (hopefully).
> Of course it won't, since you _still_ cannot fix a _missing_ library with > playing environmental games ;-) The PyQt <-> Qt dependency is resolved with > the attached patch. > You will notice, when this starts to work, because the size of your app > will grow considerably (as long as your app doesn't use QtNetwork, QtSql, > QtXml, QtSvg, or Qt3Support, yet). They all get pulled with the full > qt4_plugins support (see my list), but as you said before, they're handled > as data files ATM, which is the root of the problem.
Ah, so you're basically saying that the plugins *themselves* bring in additional dependencies, so, if we don't make them go through bindepend.py, we might miss some library. Interesting, I had not thought of that :)
BTW, I would like the plugin support to be exposed somehow to the suer. For instance, I would like PyInstaller users to be able to specify in their spec files which plugins they do really need. I'm not sure how it could work though. I'll think of something. -- Giovanni Bajo Develer S.r.l. http://www.develer.com