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

Implement f{32,64}.{min,max} instructions #472

Merged
merged 5 commits into from
Aug 14, 2020
Merged

Implement f{32,64}.{min,max} instructions #472

merged 5 commits into from
Aug 14, 2020

Conversation

chfast
Copy link
Collaborator

@chfast chfast commented Aug 11, 2020

image

@chfast chfast requested review from axic and gumb0 August 11, 2020 11:10
@chfast chfast marked this pull request as draft August 11, 2020 11:25
{
if (std::isnan(a))
return a;
if (std::isnan(b))
Copy link
Member

@axic axic Aug 11, 2020

Choose a reason for hiding this comment

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

Are there any spectests deciding this order? e.g. what happens if both are nan?

To be clear: is there a possibility to have different kind of nans here?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Yes. The standard NaN propagation rules apply.

@chfast
Copy link
Collaborator Author

chfast commented Aug 11, 2020

Has bugs.

@@ -264,6 +264,8 @@ TYPED_TEST(execute_floating_point_types, binop_nan_propagation)
constexpr Instr opcodes[] = {
Instr::f32_add,
Instr::f32_div,
Instr::f32_min,
Instr::f32_max,
Copy link
Member

Choose a reason for hiding this comment

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

The spec says nothing about canonical nans, yet all these tests below pass?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

It does. Implicitly, by using nans_N{} pseudo-function. I.e. if all NaN inputs are canonical NaNs the output must be a canonical NaN as well. Otherwise, an arithmetic NaN is fine.

auto instance = instantiate(parse(this->get_binop_code(Instr::f32_min)));

// Check every pair from cartesian product of the list of values.
for (size_t i = 0; i < std::size(this->ordered_special_values); ++i)
Copy link
Member

Choose a reason for hiding this comment

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

While using this list is nice, I think having explicit test cases based on the spec (in the opening commit) would be useful.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Duplicating the same checks is less confusing?

Copy link
Member

Choose a reason for hiding this comment

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

I'm not sold on this list, it is a pain looking it up every single time.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Done.

@codecov
Copy link

codecov bot commented Aug 13, 2020

Codecov Report

Merging #472 into master will increase coverage by 0.00%.
The diff coverage is 100.00%.

@@           Coverage Diff            @@
##           master     #472    +/-   ##
========================================
  Coverage   99.54%   99.55%            
========================================
  Files          54       54            
  Lines       16368    16494   +126     
========================================
+ Hits        16294    16420   +126     
  Misses         74       74            

if (std::isnan(b))
return b;
if (std::isnan(a) || std::isnan(b))
return std::numeric_limits<T>::quiet_NaN();
Copy link
Member

Choose a reason for hiding this comment

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

Where did this manifest itself as an error?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

In the NaN propagation test - for signaling NaN inputs, we must return an arithmetic NaN.

inline constexpr T fmin(T a, T b) noexcept
{
if (std::isnan(a) || std::isnan(b))
return std::numeric_limits<T>::quiet_NaN();
Copy link
Collaborator

Choose a reason for hiding this comment

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

Is it guaranteed that it's a canonical NaN? I know we have a test for that, but maybe it's worth a static_assert?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

No. But I don't have a way to check it here.

@chfast chfast merged commit 64a4c88 into master Aug 14, 2020
@chfast chfast deleted the fp_minmax branch August 14, 2020 11:03
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants