[Kde-bindings] Progress report on Py*5 binding generation
Stephen Kelly
steveire at gmail.com
Thu Apr 21 22:29:24 UTC 2016
Shaheed Haque wrote:
>> To that end, in addition to sip/kselectionproxymodel.sip I now have:
>>
>> $ cat sip/kitemmodelsmod.sip
>>
>> %Module PyKDE5.kitemmodels
>>
>> %ModuleHeaderCode
>> #pragma GCC visibility push(default)
>> %End
>>
>> %Import QtCore/QtCoremod.sip
>>
>> %Include kselectionproxymodel.sip
>>
>>
>> Is this what I am supposed to do? Here is the output I get when
>> attempting to use it:
>
> Yeeessss...it is a bit tricky...
>
> First, if you use the "-v" flag to the sip_compiler.py, it will show you
> the exact command like for SIP and later the C++ compiler/linker. That
> might help you see what is going on.
Yes, that's good, thanks.
> The %Feature thing you may be able to ignore. It is used along with the
> SIP compiler's -x (lower case X) option to try to work around the problem
> where in KF5, you often get AAAmod.sip and BBBmod.sip which need to import
> each other
You have alluded to this several times, but you have never stated which
modules form a cycle like this. Which KF5 libraries have this cycle?
> ...I used the SIP compiler's -X (upper case X) option to extract the
> %Extract data, and generate the "-I foo -I bar" paths for the C++
> compiler. So, you can just put a %Extract section like this into your
> file:
>
> %Extract(id=includes)
> /usr/include/KF5/KDBusAddons
> /usr/include/x86_64-linux-gnu/qt5/QtCore
> /usr/include/x86_64-linux-gnu/qt5/QtDBus
> %End
As the file might be generated by cmake, this might work, but it seems
easier to pass the include directories on the command line. The includes
will be different on each platform.
After hacking the sip_compiler a bit I can do this:
./sip_compiler.py -v --includes "/usr/include/x86_64-linux-
gnu/qt5,/usr/include/x86_64-linux-gnu/qt5/QtCore" --select
@kitemmodelsmod.sip sip cxx
My hacking is quite dirty, but you can extract feature requests from it,
namely, don't require the include/extract stuff.
The makefile manipulation stuff can be ignored, because the SIP generated
makefiles won't play nicely with cmake, but should be easily able to
generate our own makefiles/ninja build files.
diff --git a/sip_generation/sip_compiler.py b/sip_generation/sip_compiler.py
index 057dfe9..715f9c4 100755
--- a/sip_generation/sip_compiler.py
+++ b/sip_generation/sip_compiler.py
@@ -133,20 +133,23 @@ class CxxDriver(object):
if line.startswith("%Module"):
feature_list = os.path.join(self.input_dir,
"modules.features")
tmp = set()
- with open(feature_list, "rU") as f:
- for feature in f:
- if feature not in tmp:
- tmp.add(feature)
- o.write(feature)
+ # with open(feature_list, "rU") as f:
+ # for feature in f:
+ # if feature not in tmp:
+ # tmp.add(feature)
+ # o.write(feature)
logger.debug(modified_source)
feature = sip_file.replace(os.path.sep, "_").replace(".", "_")
- cmd = [self.sipconfig.sip_bin, "-c", full_output, "-b",
build_file, "-x", feature, "-X",
- INCLUDES_EXTRACT + ":" + module_includes] +
self.pyqt_sip_flags + sip_roots + [modified_source]
+ cmd = [self.sipconfig.sip_bin, "-c", full_output, "-b",
build_file, "-x", feature] + self.pyqt_sip_flags + sip_roots +
[modified_source]
self._run_command(cmd)
#
# Create the Makefile.
#
- module_includes = self.includes + open(module_includes,
"rU").read().split("\n")
+ module_includes = self.includes
+ try:
+ module_includes += open(module_includes,
"rU").read().split("\n")
+ except:
+ pass
self.sipconfig._macros["INCDIR"] = " ".join(module_includes)
makefile = sipconfig.SIPModuleMakefile(self.sipconfig,
build_file, makefile=make_file)
#
@@ -155,6 +158,9 @@ class CxxDriver(object):
# ".dll" extension on Windows).
#makefile.extra_libs = ["KParts"]
#
+ makefile.extra_cxxflags = ["-std=c++14"]
+ makefile.extra_lflags = ["-std=c++14", "-Wl,--fatal-warnings",
"-Wl,--no-undefined"]
+ makefile.extra_libs = ["m /usr/lib/x86_64-linux-
gnu/libQt5Core.so /usr/lib/x86_64-linux-gnu/libKF5ItemModels.so
/usr/lib/x86_64-linux-gnu/libpython2.7.so"]
makefile.generate()
self._run_command(["make", "-f", os.path.basename(make_file)],
cwd=full_output)
except Exception as e
With that done here is my output:
$ ./sip_compiler.py -v --includes "/usr/include/x86_64-linux-
gnu/qt5,/usr/include/x86_64-linux-gnu/qt5/QtCore" --select
@kitemmodelsmod.sip sip cxx
2016-04-22 00:23:01,282 __main__ INFO: Creating cxx/
2016-04-22 00:23:01,283 __main__ DEBUG: cxx/kitemmodelsmod.sip.tmp
2016-04-22 00:23:01,283 __main__ INFO: /usr/bin/sip -c cxx/ -b
cxx/module.sbf -x kitemmodelsmod_sip -x VendorID -t WS_X11 -t Qt_5_4_2 -x
Py_v3 -I/usr/share/sip/PyQt5 -Isip cxx/kitemmodelsmod.sip.tmp
2016-04-22 00:23:01,728 __main__ INFO: make -f module.Makefile
g++ -c -std=c++14 -g -O2 -fstack-protector-strong -Wformat -Werror=format-
security -D_FORTIFY_SOURCE=2 -fPIC -Wall -W -DNDEBUG -I. -
I/usr/include/x86_64-linux-gnu/qt5 -I/usr/include/x86_64-linux-
gnu/qt5/QtCore -I/usr/include/python2.7 -o sipkitemmodelscmodule.o
sipkitemmodelscmodule.cpp
g++ -c -std=c++14 -g -O2 -fstack-protector-strong -Wformat -Werror=format-
security -D_FORTIFY_SOURCE=2 -fPIC -Wall -W -DNDEBUG -I. -
I/usr/include/x86_64-linux-gnu/qt5 -I/usr/include/x86_64-linux-
gnu/qt5/QtCore -I/usr/include/python2.7 -o
sipkitemmodelsKSelectionProxyModel.o sipkitemmodelsKSelectionProxyModel.cpp
g++ -std=c++14 -Wl,--fatal-warnings -Wl,--no-undefined -Wl,-Bsymbolic-
functions -Wl,-z,relro -shared -Wl,--version-script=kitemmodels.exp -o
kitemmodels.so sipkitemmodelscmodule.o sipkitemmodelsKSelectionProxyModel.o
-lm /usr/lib/x86_64-linux-gnu/libQt5Core.so /usr/lib/x86_64-linux-
gnu/libKF5ItemModels.so /usr/lib/x86_64-linux-gnu/libpython2.7.so
That created the cxx/kitemmodels.so library
$ ls cxx/
kitemmodels.exp sipAPIkitemmodels.h
kitemmodelsmod.sip.tmp sipkitemmodelscmodule.cpp
kitemmodels.so* sipkitemmodelscmodule.o
module.Makefile sipkitemmodelsKSelectionProxyModel.cpp
module.sbf sipkitemmodelsKSelectionProxyModel.o
pythontest.py*
$ cat cxx/pythontest.py
#!/usr/bin/env python
from PyQt5 import QtCore
import kitemmodels
$ ./cxx/pythontest.py
Traceback (most recent call last):
File "./cxx/pythontest.py", line 5, in <module>
import kitemmodels
SystemError: dynamic module not initialized properly
Is there some other step to take before that import will work?
Thanks,
Steve.
More information about the Kde-bindings
mailing list