[Cython] Cygwin: Handling missing C99 long double functions

Robert Bradshaw robertwb at math.washington.edu
Tue May 10 02:01:36 EDT 2016


On Wed, May 4, 2016 at 8:01 AM, Erik Bray <erik.m.bray at gmail.com> wrote:
> On Tue, May 3, 2016 at 7:15 PM, Robert Bradshaw <robertwb at gmail.com> wrote:
>> On Tue, May 3, 2016 at 3:04 AM, Erik Bray <erik.m.bray at gmail.com> wrote:
>>> I agree that it would be safest not to use long double where long
>>> double functions are not support, and an application that does should
>>> probably check for that.
>>>
>>> The problem is that Cython is generating code that simply *cannot* be
>>> compiled on such platforms.
>>
>> Does Cython ever generate such code when long doubles are not used in the
>> source? If so, we should fix that. But I don't think Cython should be
>> swapping in double versions for long double operations.
>
> No, but the problem is that Cython is a pretty heavy layer of
> abstraction.  In the example I gave no long double function was ever
> used explicitly--it was added by a compiler optimization.  I probably
> wouldn't write that code thinking that I will need a workaround on
> platforms that don't have truncl.

I would argue that if you don't have truncl, you shouldn't be using
long double. Possibly this particular use of truncl could be worked
around (though note that using trunc is not safe) but it's starting to
get on shaky ground.

> In the slightly more explicit cases of fmod and pow I might agree.
> Though there still isn't a great way to anticipate the need to write
> separate handling for long double functions into a module, for a
> platform that doesn't support them.  I can't write something in a
> Cython module like:
>
>     if sys.platform != 'cygwin':
>         def my_long_double_func(long double x):
>             ....

No, that's not something we support well. You can put them in a
separate module and conditionally compile/import them.

> Maybe would be nice to have a simple compiler directive that outright
> disables compiling a function depending on a platform check. (I think
> this would also be useful for the test framework--the current system
> of module-level tags is not fine-grained as I would like, I'm finding.
>
>>> My suggestion would be to replace the
>>> current calls to [trunc,fmod,pow]l to the appropriate
>>> __Pyx_%(func)_%(type) wrapper which would provide two alternatives:
>>> One that works properly, and one that falls back to using the double
>>> version of the function (Numpy does this so there is some precedent).
>>> I would go further and suggest throwing up a pre-compiler warning when
>>> using the double versions.
>>>
>>> The only question is what condition (in my mind) is what to use as a
>>> condition for selecting the fallbacks.  For now I'm thinking something
>>> quite specific like
>>>
>>>     #if defined(__CYGWIN__) && defined(_LDBL_EQ_DBL)
>>>
>>> since I'm apparently the only person who cares about this at the
>>> moment, and Cygwin is the platform I'm targeting.
>>>
>>> Again, my only real concern right now is that Cython generates code
>>> that can be compiled on Cygwin.
>>
>>
>> If you want this behavior, wouldn't including a header
>>
>> #if defined(__CYGWIN__) && defined(_LDBL_EQ_DBL)
>> #define truncl trunc
>> #define fmodl fmod
>> #define powl pow
>> #endif
>>
>> as part of your package do the job?
>
> That's a reasonable workaround. But I would argue that should be baked
> into Cythonized code, at least optionally, and should generate a
> warning.

This is dangerous to bake into Cython code, even with a warning (who
would see it?) I say if you want to pretend to support long double on
platforms that don't fully support long double, that should be very
explicit.


More information about the cython-devel mailing list