New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Fix python global object constants #250
Conversation
Test case is slightly modified from the test case in issue #250 Use of constant objects does not seem to work in Python - the type is SwigPyObject instead of constant_directive.Type1.
Fix for Python and -builtin Fix from Github issue #250
Tweak to previous commit from issue #250 for C compatibility. Set self to zero too.
%constant and structs isn't really supported from what I can see. I'm not convinced there is a great need for them either. Nevertheless the 3 commits mentioned above improve matters and should get them working for the vast majority of languages. Although your patch fixes the problem for python -builtin, I added in a test case in 70a04c9. The corresponding runtime testcase should be in constant_directive_runme.py as follows: import constant_directive
print("TYPE1_CONSTANT1 type: {}".format(type(constant_directive.TYPE1_CONSTANT1)))
print("getType1Instance() type: {}".format(type(constant_directive.getType1Instance())))
if constant_directive.TYPE1_CONSTANT1.val != 1:
raise RuntimeError("fail")
if constant_directive.TYPE1_CONSTANT2.val != 2:
raise RuntimeError("fail")
if constant_directive.TYPE1_CONSTANT3.val != 3:
raise RuntimeError("fail") which does work for -builtin, but fails using default options. The output is
I think there is some sort of initialisation ordering problem registering the types, but I havn't looked further and don't have the inclination to do so atm. |
@wsfulton, I think I found the cause for struct constant having no user-defined attributes in python. This is about how constants are spawned. This is what I see for the struct-constants in TYPE1_CONSTANT1 = _constant_directive.TYPE1_CONSTANT1
# ... The class Type1(_object):
__swig_setmethods__ = {}
__setattr__ = lambda self, name, value: _swig_setattr(self, Type1, name, value)
__swig_getmethods__ = {}
__getattr__ = lambda self, name: _swig_getattr(self, Type1, name)
__repr__ = _swig_repr
def __init__(self, val=0):
this = _constant_directive.new_Type1(val)
try:
self.this.append(this)
except:
self.this = this
__swig_setmethods__["val"] = _constant_directive.Type1_val_set
__swig_getmethods__["val"] = _constant_directive.Type1_val_get
if _newclass:
val = _swig_property(_constant_directive.Type1_val_get, _constant_directive.Type1_val_set)
__swig_destroy__ = _constant_directive.delete_Type1
__del__ = lambda self: None
Type1_swigregister = _constant_directive.Type1_swigregister
Type1_swigregister(Type1) An example python variable created by: t = Type1(); will have all the attributes exposed to python, but _constant_directive.TYPE1_CONSTANT1 lacks the Shouldn't swig create struct contants by creating "fully-fledged" python variables instead of references to some internal stuff? What I try to say is to do this:
in the shadow file. |
Ok, I have to correct myself. After digging a little I came to conclusion, that without
so the current approach of setting the constants inside of |
Yes, that is what I suspected, the constants should be created after the initialisation/registration of the types. |
0e434b2
to
9089081
Compare
Got it working (with, and without |
ca5d440
to
88df298
Compare
I think it may be reviewed and eventually merged. For some reason, the octave build failed on travis-ci (gcc internal compiler error), but I think it's not related to this PR. |
The Octave build sometimes fails and is irrelevant to this. Without -builtin, the following in the constant_directive.i testcase: %constant Type1 TYPE1_CONSTANT1; generates: _constant_directive.TYPE1_CONSTANT1_swigregister(_constant_directive)
TYPE1_CONSTANT1_swigregister = _constant_directive.TYPE1_CONSTANT1_swigregister
TYPE1_CONSTANT1 = _constant_directive.TYPE1_CONSTANT1 I can't see the point of the 2nd line. Have I missed something? The TYPE1_CONSTANT1_swigregister function isn't registering types like Type1_swigregister is. I suggest it uses a different suffix, eg _swigconstant. In the generated code, can you replace 'm' with 'module' to be clearer what it is. Can you adapt it to use the standard code formatting spacing , eg PyObject * instead of PyObject* and 'if (' instead of 'if('. Can you also ensure it works when using the various python optimisation flags (-O -modernargs -classic etc). Can you also modify constant_directive_runme.py and move the info in the print statements into the RuntimeError. |
I've seen similar line to the second in the *_swigregister calls for types. I thought there is some convention to "import" names of *_swigregister (and such) functions to shadow files, so just followed this. I agree it would be better to remove this line, so I'm going to do this quickly. I'll also change swigregister to swigconstant and follow other adwices too. |
I have updated this PR following all your suggestions. I've also ran tests for some arbitrarily choosen combinations of swig flags. My test run script and the results may be found here. There is some problem with |
029aab8
to
2f6dee3
Compare
Ok, I have fixed the issue with |
-builtin should not be used with many of the other flags like -modern, but then again, SWIG shouldn't seg fault if this is attempted! Thanks, for the update, I'm about to merge them in. |
Thank you for merging. I just want to make a remark about segfault. It happens when we use |
* master: Add Scilab to README file C++11 mention in doc Introduction html fixes Add release info for 3.0.5 Update changes file Fix python tests for old versions of Python Test-suite fixes for python -classic Fix Python -classic and property setting Python C89 fix mixed code and declarations compiler error in constants code from patch #250 Conflicts: .travis.yml
With current swig the following simple test case
does not compile, when generated with
-builtin
option. The compilation error is:This patch fixes the problem.
Advice needed: I've set
self
tom
(module) but maybe it should beNULL
? Please advise.