Skip to content
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

std.math: Use core.stdc.fenv for exception mask values #4272

Merged
merged 1 commit into from
Oct 8, 2017

Conversation

ibuclaw
Copy link
Member

@ibuclaw ibuclaw commented Apr 30, 2016

See also: dlang/druntime#1554

FloatingPointControl rounding control and interrupt masks should be given similar treatment. Where their values all correspond to macros from fpu_control.h in libc (there does exist any binding in druntime).

@ibuclaw
Copy link
Member Author

ibuclaw commented May 1, 2016

Can someone check the fenv header for win32? Should it be the same as CRuntime_Microsoft or not?

std/math.d Outdated
UNDERFLOW_MASK = FE_UNDERFLOW,
OVERFLOW_MASK = FE_OVERFLOW,
DIVBYZERO_MASK = FE_DIVBYZERO,
INVALID_MASK = FE_INVALID
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why do we even need those? Wouldn't it be better to directly replace all occurrences?
As far as I can tell the enum is private

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

One change at a time. ;-)

But yeah they probably should go away.

@ibuclaw
Copy link
Member Author

ibuclaw commented May 1, 2016

Ah, it is win64 that is failing. Ping @kinke as you added that path. Why does Win64 deviate from hardware?

@kinke
Copy link
Contributor

kinke commented May 1, 2016

fenv.h from Windows 10 Universal C Runtime (shipped with Visual Studio 2015), no special #ifdefs:

#define FE_INEXACT   _SW_INEXACT       // _EM_INEXACT     0x00000001 inexact (precision)
#define FE_UNDERFLOW _SW_UNDERFLOW     // _EM_UNDERFLOW   0x00000002 underflow
#define FE_OVERFLOW  _SW_OVERFLOW      // _EM_OVERFLOW    0x00000004 overflow
#define FE_DIVBYZERO _SW_ZERODIVIDE    // _EM_ZERODIVIDE  0x00000008 zero divide
#define FE_INVALID   _SW_INVALID       // _EM_INVALID     0x00000010 invalid

Since when does MS not like to go their own way? 😁

So I'd probably keep the fixed constants for X86 to work around this CRuntime_Microsoft special case and use the fenv constants for all other architectures.

@ibuclaw
Copy link
Member Author

ibuclaw commented May 1, 2016

OK, finally found a reference header:
https://github.com/adityaramesh/concurrency_runtime/blob/c92c41b8ff41657a164c7760fd67b77d84ba766f/VS2013_SP2/include/fenv.h#L39-L45

How does this work? It's the CPU that sets the flags, not the OS. 😕

@ibuclaw
Copy link
Member Author

ibuclaw commented Jan 15, 2017

Ping? (I should add a comment here about why windows is a special case)

@ibuclaw
Copy link
Member Author

ibuclaw commented Jan 20, 2017

This depends on druntime change getting in first before this - at least for non-x86. This is just moving enum values to their proper locations in the stdc bindings. I am disappointed at Microsoft though for having masks that don't match the hardware.

I should probably replace X86_Any here with just CRuntime_Microsoft.

@MetaLang
Copy link
Member

MetaLang commented Aug 6, 2017

@ibuclaw is this the Druntime PR you're referring to? dlang/druntime#1554

@ibuclaw
Copy link
Member Author

ibuclaw commented Aug 6, 2017

@MetaLang - Yes... I should update the druntie PR to include the vagary of architectures we've added support for since then.

(By the way, isn't the link in my original post working?)

@MetaLang
Copy link
Member

MetaLang commented Aug 6, 2017

@ibuclaw yeah it does. Sorry, I was half asleep when I wrote that.

@wilzbach
Copy link
Member

wilzbach commented Aug 6, 2017

I was half asleep when I wrote that.

Don't worry about this. Many people including myself have the same problem of finding time and often the night is the only available spot :/

Copy link
Member

@PetarKirov PetarKirov left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, apart from my question about removing the version (X86_Any) definitions altogether and using only the aliases like INEXACT_MASK = FE_INEXACT which forward to druntime.

With that fixed, this should be good to go.

std/math.d Outdated
uint flags;

version (X86_Any)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we remove these constants too, as they should now be pulled from Druntime?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See earlier conversation on Windows being annoyingly different, which causes testsuite failures.

Copy link
Member

@PetarKirov PetarKirov Aug 7, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you add some short explanation as a comment, so that people won't be tempted to "improve" the code?

Copy link
Contributor

@kinke kinke Aug 7, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Proposal:

// Microsoft uses hardware-incompatible custom constants in fenv.h (core.stdc.fenv).

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also, there's my suggestion of using version CRuntime_Microsoft.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[Microsoft is gonna try again with Windows on ARM, so CRuntime_Microsoft may not always imply x86(_64).]

That's fine, because it will probably use the same constants for both x86 and ARM. :-)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A daring assumption. ;)

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we move CRuntime_Microsoft to druntime? And if necessary add version (X86_Any) and version (ARM) inside.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It already is in druntime, but as stated before, the Microsoft headers don't appear to match the hardware. And so the duplication is an unfortunate evil.

Maybe there's a rational explanation like Microsoft get and set feflags differently, or mask them somehow to translate to the "correct" values. Correct being in quotation marks.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll get round to actually rebasing this tonight, rather than talking about it in passing.

@ibuclaw
Copy link
Member Author

ibuclaw commented Oct 8, 2017

I've just hit this again whilst getting mips CI working with gdc. Can we merge this, glossing over the fac tthat CRuntime_Microsoft is different? (Shame on you Microsoft).

@dlang-bot
Copy link
Contributor

Thanks for your pull request, @ibuclaw!

Bugzilla references

Your PR doesn't reference any Bugzilla issue.

If your PR contains non-trivial changes, please reference a Bugzilla issue or create a manual changelog.

@ibuclaw ibuclaw force-pushed the ieeefenvflags branch 2 times, most recently from ac2fc30 to e95ec1b Compare October 8, 2017 15:03
@ibuclaw
Copy link
Member Author

ibuclaw commented Oct 8, 2017

Rebased against master.

std/math.d Outdated
{
// SPARC FSR is a 32bit register
//(64 bits for Sparc 7 & 8, but high 32 bits are uninteresting).
import core.stdc.fenv;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Circle CI fails:

std/math.d(4682:16)[warn]: Local imports should specify the symbols being imported to avoid hiding local symbols.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll just statically import it. There are a few other places where std.math overlaps with core.stdc.fenv.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants