Re: 2.0.4 -> 3.0.12 -> 4.0.1
Bob Hood <[email protected]>
| Newsgroups | gmane.comp.programming.swig |
|---|---|
| Message-ID | <[email protected]> |
Ok, after a week of crickets and tumbleweeds, I realized I was probably, once
again, blazing some kind of new trail with SWIG and Python. I dug into the
problem today, and found out that it's actually a...well, we'll call it a
"misunderstanding"...in the Python 3.8.2 code. When creating a new object,
Python 3.8.2 first invokes a function called excess_args(). This function has
no humor at all about being provided Py_None values for args and kwds:
return PyTuple_GET_SIZE(args) ||
(kwds && PyDict_Check(kwds) && PyDict_GET_SIZE(kwds));
Well, SWIG 3.0.12's SWIG_Python_NewShadowInstance() function happily sends
Py_None for thsese value (see the original post at the bottom). This, of
course, trips the assert in the PyTuple_GET_SIZE() function when it does a
sanity check on the provided value. I patched excess_args() to do the proper
data checking:
return (args && PyTuple_Check(args) && PyTuple_GET_SIZE(args)) ||
(kwds && PyDict_Check(kwds) && PyDict_GET_SIZE(kwds));
And this particular problem I was encountering with SWIG 3.0.12 is now gone.
I'll be moving forward with this version of SWIG then, and hopefully SWIG v4
will get its indentation issues addressed at some point in the future.
On 4/14/2020 11:42 AM, Bob Hood wrote:
> This is a tale of woe, a tale of migration and tribulation.
>
> I have for many years now been maintaining the integration of Python v2.7
> into our application using SWIG 2.0.4. All has been roses. With the demise
> of Python2, we are of course needing to migrate to Python3. I have
> successfully (well, I /thought/ successfully) integrated Python v3.8 into
> our application using SWIG 3.0.2. (Aside: Why 3.0.2? Because that's the
> version that was available when I did the initial work, and I have just
> recently resurrected that work from an inactive branch.) Everything looked
> good, until I attempted to run a Python script that interfaces with SWIG
> Directors. This otherwise battle-tested code triggered an exception in
> Python 3.8 having to do with "PyCheck_Tuple(args)" when my C++ code
> attempted to execute a Directors function:
>
> try
> {
> ...
> PCore::LWLayoutGeneric access(l);
> result = plugin->process(&access);
> } catch (...)
> {
> check_python_error();
> }
>
> The "plugin" instance here is a C++ stub class that Python wraps, and which
> the Directors function overrides:
>
> virtual int process(PCore::LWLayoutGeneric*)
> {
> return AFUNC_OK;
> }
>
> Walking through the SWIG-generated C++ code, the steps are:
>
> 1. Swig_Director_IGeneric::process() invokes SWIG_NewPointerObj()
>
> 2. SWIG_NewPointerObj() invokes SWIG_Python_NewShadowInstance()
>
> if (robj && clientdata && !(flags & SWIG_POINTER_NOSHADOW)) {
> PyObject *inst = SWIG_Python_NewShadowInstance(clientdata, robj);
>
> 3. SWIG_Python_NewShadowInstance() detects the Python version as being ">=
> 0x03000000" and then calls:
>
> inst = ((PyTypeObject*) data->newargs)->tp_new((PyTypeObject*)
> data->newargs, Py_None, Py_None);
>
> which triggers an assert in the python38 shared library:
>
>
>
>
>
> Enter SWIG 4.0.1. I decided to try it as a drop-in replacement for 3.0.12.
> Unfortunately, the import module that it creates does not get the formatting
> correct, leaving indentation errors /all over the module/:
>
>
>
>
>
> So, of course, I cannot even run the system to see if SWIG v4 solves the
> /original/ issue found in SWIG v3.
>
> As I mentioned, this code was production-tested with Python v2 & SWIG 2.0.4.
> Any insights on what I might adjust to get SWIG v3 to function properly? Or
> could this be just some kind of bug in that version, and I should focus on
> SWIG v4 when it's working?
>
>
>
> _______________________________________________
> Swig-user mailing list
> [email protected]
> https://lists.sourceforge.net/lists/listinfo/swig-user
_______________________________________________
Swig-user mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/swig-user