On 2 October 2013 14:51, Vadim Zeitlin <vzswig@...> wrote:
> Hello,
>
> This is another weird bug report which only I seem to be encountering (not
> intentionally, believe me). Please consider this example:
>
> % cat n et.i
> 1 %module et
> 2
> 3 template <typename T> struct T {};
> 4
> 5 %naturalvar T<E>;
> 6 %template(TE) T<E>;
> 7
> 8 %inline { enum E { E1, E2, E3 }; }
> 9
> 10 %typemap(csvarout, excode=SWIGEXCODE2) const T<E>& %{
> 11 get {
> 12 // Intentionally don't use excode here to trigger a
> warning if this
> 13 // typemap is used.
> 14 return $imcall;
> 15 }%}
> 16
> 17 %inline {
> 18 struct S {
> 19 T<E> ee;
> 20 };
> 21 }
>
> This works as expected, i.e.
>
> % swig csharp c++ o wrap_et_csharp.cpp et.i
> et.i:19: Warning 844: C# exception may not be thrown  no $excode
> or excode attribute in 'csvarout' typemap.
>
> As the warning indicates, the typemap is used and everything is fine.
>
> Now exchange the line #8, with the enum declaration, and the line #6 and
> rerun swig. Now the typemap is not used any more. And there doesn't seem to
> be any way to make SWIG handle "ee" naturally if the enum declaration comes
> before the %template line short of using either "naturalvar" command line
> option or parameterless "%naturalvar" (which both result in other problems
> elsewhere in my code and so I'd like to avoid them).
>
> I've tried all the possible orders of the different lines keeping the enum
> declaration at the top (again, because this is where it appears in my real
> code and it's not trivial to change this as enum comes from a header
> included from another header from another module...) without success. I
> also tried using "%naturalvar TE" in desperation but it doesn't work
> neither (which is at least somewhat reassuring). Conversely, any order with
> %template coming before the enum declaration does work.
>
> This definitely looks like a bug in SWIG to me, especially because if you
> replace "enum E { ... }" with "struct E {}", everything works just fine, in
> whatever order. But, as usual, I have absolutely no idea where to start
> looking for it.
>
> Any hints/ideas?
>
>
The debugtmsearch option is really useful for this kind of problem. In
the first case, you'll see:
example.i:22: Searching for a suitable 'csvarout' typemap for: T< E >
const &S::ee
Looking for: T< E > const &S::ee
Looking for: T< E > const &ee
Looking for: T< E > const &
Using: %typemap(csvarout) T< E > const &
indicating your typemap is being used as you observed. Swapping lines #6
and #8 gives:
example.i:22: Searching for a suitable 'csvarout' typemap for: T< E > *S::ee
Looking for: T< E > *S::ee
Looking for: T< E > *ee
Looking for: T< E > *
Looking for: T *S::ee
Looking for: T *ee
Looking for: T *
Looking for: T< enum E > *S::ee
Looking for: T< enum E > *ee
Looking for: T< enum E > *
Looking for: T *S::ee
Looking for: T *ee
Looking for: T *
Looking for: SWIGTYPE *S::ee
Looking for: SWIGTYPE *ee
Looking for: SWIGTYPE *
Using: %typemap(csvarout) SWIGTYPE *
Which should explain why your typemap is not being found  %naturalvar is
not having any effect and it is looking for a different type. It gives a
clue as to what to do to fix though, change line #10 to:
%typemap(csvarout, excode=SWIGEXCODE2) const T<E>&, T<E>* %{
then you get a match, tada!
example.i:22: Searching for a suitable 'csvarout' typemap for: T< E > *S::ee
Looking for: T< E > *S::ee
Looking for: T< E > *ee
Looking for: T< E > *
Using: %typemap(csvarout) T< E > *
Quite why T<E>* is required instead of const T<E>& even though you have
%naturalvar, is not clear to me without looking further into %naturalvar
with enums.
William
