*[PATCH] Handle > INF and < INF correctly in range-op-float.cc@ 2022-09-06 7:29 Aldy Hernandez2022-09-06 7:35 ` Jakub Jelinek 0 siblings, 1 reply; 11+ messages in thread From: Aldy Hernandez @ 2022-09-06 7:29 UTC (permalink / raw) To: GCC patches;+Cc:Richard Biener, Jakub Jelinek, Andrew MacLeod, Aldy Hernandez The gfortran.dg/minlocval*.f90 tests are generating conditionals past the infinities. For example: if (x <= +Inf) foo (x); else bar (x); It seems to me that the only possible value for x on the false side is either NAN or undefined (for !HONOR_NANS). Is this correct, or is there some other FP nuance I'm unaware of? gcc/ChangeLog: * range-op-float.cc (build_lt): Handle < -INF. (build_gt): Handle > +INF. gcc/testsuite/ChangeLog: * gcc.dg/tree-ssa/vrp-float-inf-1.c: New test. --- gcc/range-op-float.cc | 18 ++++++++++++++++++ .../gcc.dg/tree-ssa/vrp-float-inf-1.c | 15 +++++++++++++++ 2 files changed, 33 insertions(+) create mode 100644 gcc/testsuite/gcc.dg/tree-ssa/vrp-float-inf-1.c diff --git a/gcc/range-op-float.cc b/gcc/range-op-float.cc index 050f07a9867..4515bbf0b7e 100644 --- a/gcc/range-op-float.cc +++ b/gcc/range-op-float.cc @@ -235,6 +235,15 @@ build_le (frange &r, tree type, const REAL_VALUE_TYPE &val) static void build_lt (frange &r, tree type, const REAL_VALUE_TYPE &val) { + if (real_isinf (&val, 1)) + { + if (HONOR_NANS (type)) + frange_set_nan (r, type); + else + r.set_undefined (); + return; + } + // Hijack LE because we only support closed intervals. build_le (r, type, val); } @@ -252,6 +261,15 @@ build_ge (frange &r, tree type, const REAL_VALUE_TYPE &val) static void build_gt (frange &r, tree type, const REAL_VALUE_TYPE &val) { + if (real_isinf (&val, 0)) + { + if (HONOR_NANS (type)) + frange_set_nan (r, type); + else + r.set_undefined (); + return; + } + // Hijack GE because we only support closed intervals. build_ge (r, type, val); } diff --git a/gcc/testsuite/gcc.dg/tree-ssa/vrp-float-inf-1.c b/gcc/testsuite/gcc.dg/tree-ssa/vrp-float-inf-1.c new file mode 100644 index 00000000000..1d21cce41e6 --- /dev/null +++ b/gcc/testsuite/gcc.dg/tree-ssa/vrp-float-inf-1.c @@ -0,0 +1,15 @@ +// { dg-do compile } +// { dg-options "-O2 -fdump-tree-evrp-details" } + +void foo (); +void bar (double); + +void funky(double f, double g) +{ + if (f <= __builtin_inf ()) + foo (); + else + bar (f); +} + +// { dg-final { scan-tree-dump-not " Inf, Inf" "evrp" } } -- 2.37.1 ^ permalink raw reply [flat|nested] 11+ messages in thread

*Re: [PATCH] Handle > INF and < INF correctly in range-op-float.cc2022-09-06 7:29 [PATCH] Handle > INF and < INF correctly in range-op-float.cc Aldy Hernandez@ 2022-09-06 7:35 ` Jakub Jelinek2022-09-06 7:40 ` Aldy Hernandez 0 siblings, 1 reply; 11+ messages in thread From: Jakub Jelinek @ 2022-09-06 7:35 UTC (permalink / raw) To: Aldy Hernandez;+Cc:GCC patches, Richard Biener, Andrew MacLeod On Tue, Sep 06, 2022 at 09:29:01AM +0200, Aldy Hernandez wrote: > The gfortran.dg/minlocval*.f90 tests are generating conditionals past > the infinities. For example: > > if (x <= +Inf) > foo (x); > else > bar (x); > > It seems to me that the only possible value for x on the false side is > either NAN or undefined (for !HONOR_NANS). No, none of the ==, <, <=, >, >= comparisons are ever true if one or both operands are NaN (only != will be true in those cases from the standard comparisons, when not counting UNORDERED_EXPR and the likes). So, x < -Inf or x > +Inf are always false, we just can't optimize those away without -ffast-math because they could raise an exception on sNaN. But I think not optimizing such operations away if we care about exceptions is the duty of DCE etc. Jakub ^ permalink raw reply [flat|nested] 11+ messages in thread

*Re: [PATCH] Handle > INF and < INF correctly in range-op-float.cc2022-09-06 7:35 ` Jakub Jelinek@ 2022-09-06 7:40 ` Aldy Hernandez2022-09-06 7:44 ` Jakub Jelinek 0 siblings, 1 reply; 11+ messages in thread From: Aldy Hernandez @ 2022-09-06 7:40 UTC (permalink / raw) To: Jakub Jelinek;+Cc:GCC patches, Richard Biener, Andrew MacLeod On Tue, Sep 6, 2022 at 9:35 AM Jakub Jelinek <jakub@redhat.com> wrote: > > On Tue, Sep 06, 2022 at 09:29:01AM +0200, Aldy Hernandez wrote: > > The gfortran.dg/minlocval*.f90 tests are generating conditionals past > > the infinities. For example: > > > > if (x <= +Inf) > > foo (x); > > else > > bar (x); > > > > It seems to me that the only possible value for x on the false side is > > either NAN or undefined (for !HONOR_NANS). > > No, none of the ==, <, <=, >, >= comparisons are ever true if one > or both operands are NaN (only != will be true in those cases from the > standard comparisons, when not counting UNORDERED_EXPR and the likes). > So, x < -Inf or x > +Inf are always false, we just can't optimize those > away without -ffast-math because they could raise an exception on sNaN. > But I think not optimizing such operations away if we care about exceptions > is the duty of DCE etc. No, no. I'm not talking about optimizing them away. I'm talking about representing what is going on in the IL. For example, for: if (x > 5.0) foo (x); // {5.0, +Inf] !NAN else bar (x); // [-Inf, 5.0] ?NAN So on the true side we know x is in the {5.0, +Inf] range, plus we know it can't be a NAN. On the false side we know x is either [-Inf, 5.0] or a NAN. What I'm trying to do is represent the possible ranges for the false side of: if (x <= Inf) ... Aldy ^ permalink raw reply [flat|nested] 11+ messages in thread

*Re: [PATCH] Handle > INF and < INF correctly in range-op-float.cc2022-09-06 7:40 ` Aldy Hernandez@ 2022-09-06 7:44 ` Jakub Jelinek2022-09-06 7:49 ` Aldy Hernandez 0 siblings, 1 reply; 11+ messages in thread From: Jakub Jelinek @ 2022-09-06 7:44 UTC (permalink / raw) To: Aldy Hernandez;+Cc:GCC patches, Richard Biener, Andrew MacLeod On Tue, Sep 06, 2022 at 09:40:59AM +0200, Aldy Hernandez wrote: > if (x <= Inf) This will be [-Inf, Inf] !NAN on the true side and NAN (either sign) on the false side indeed. > if (x < -Inf) will be NAN (either sign) on the true side and [-Inf, Inf] !NAN on the false side. Jakub ^ permalink raw reply [flat|nested] 11+ messages in thread

*Re: [PATCH] Handle > INF and < INF correctly in range-op-float.cc2022-09-06 7:44 ` Jakub Jelinek@ 2022-09-06 7:49 ` Aldy Hernandez2022-09-06 7:59 ` Jakub Jelinek 0 siblings, 1 reply; 11+ messages in thread From: Aldy Hernandez @ 2022-09-06 7:49 UTC (permalink / raw) To: Jakub Jelinek;+Cc:GCC patches, Richard Biener, Andrew MacLeod On Tue, Sep 6, 2022 at 9:44 AM Jakub Jelinek <jakub@redhat.com> wrote: > > On Tue, Sep 06, 2022 at 09:40:59AM +0200, Aldy Hernandez wrote: > > if (x <= Inf) > > This will be [-Inf, Inf] !NAN on the true side and > NAN (either sign) on the false side indeed. > > > if (x < -Inf) > > will be NAN (either sign) on the true side and > [-Inf, Inf] !NAN on the false side. Sweet, that's exactly what I thought, thus the patch. Furthermore, for !HONOR_NANS I would expect the NAN sides above to be UNDEFINED/unreachable. That is, the false side of x <= Inf when !HONOR_NANS is unreachable. Agreed? Aldy ^ permalink raw reply [flat|nested] 11+ messages in thread

*Re: [PATCH] Handle > INF and < INF correctly in range-op-float.cc2022-09-06 7:49 ` Aldy Hernandez@ 2022-09-06 7:59 ` Jakub Jelinek2022-09-06 11:47 ` Aldy Hernandez 0 siblings, 1 reply; 11+ messages in thread From: Jakub Jelinek @ 2022-09-06 7:59 UTC (permalink / raw) To: Aldy Hernandez;+Cc:GCC patches, Richard Biener, Andrew MacLeod On Tue, Sep 06, 2022 at 09:49:55AM +0200, Aldy Hernandez wrote: > On Tue, Sep 6, 2022 at 9:44 AM Jakub Jelinek <jakub@redhat.com> wrote: > > > > On Tue, Sep 06, 2022 at 09:40:59AM +0200, Aldy Hernandez wrote: > > > if (x <= Inf) > > > > This will be [-Inf, Inf] !NAN on the true side and > > NAN (either sign) on the false side indeed. > > > > > if (x < -Inf) > > > > will be NAN (either sign) on the true side and > > [-Inf, Inf] !NAN on the false side. > > Sweet, that's exactly what I thought, thus the patch. > > Furthermore, for !HONOR_NANS I would expect the NAN sides above to be > UNDEFINED/unreachable. That is, the false side of x <= Inf when > !HONOR_NANS is unreachable. In practice, there is no real format that has NaNs and doesn't have Infs or vice versa and similarly we have just one switch to cover both Infinities and NaNs, so either both are supported, or neither of them, or both are supported but neither of them should appear in a valid program (-ffinite-math-only on most floating point formats). So the answer in that case is a little bit fuzzy because one shouldn't compare against infinity in that case (or for !MODE_HAS_INFINITIES even can't). But sure, if NaNs aren't possible or can't appear and you compare x <= Largest_possible_float, then it is always true and so UNDEFINED on the false edge. Jakub ^ permalink raw reply [flat|nested] 11+ messages in thread

*Re: [PATCH] Handle > INF and < INF correctly in range-op-float.cc2022-09-06 7:59 ` Jakub Jelinek@ 2022-09-06 11:47 ` Aldy Hernandez2022-09-06 12:06 ` Jakub Jelinek 0 siblings, 1 reply; 11+ messages in thread From: Aldy Hernandez @ 2022-09-06 11:47 UTC (permalink / raw) To: Jakub Jelinek;+Cc:GCC patches, Richard Biener, Andrew MacLeod [-- Attachment #1: Type: text/plain, Size: 2106 bytes --] On Tue, Sep 6, 2022 at 9:59 AM Jakub Jelinek <jakub@redhat.com> wrote: > > On Tue, Sep 06, 2022 at 09:49:55AM +0200, Aldy Hernandez wrote: > > On Tue, Sep 6, 2022 at 9:44 AM Jakub Jelinek <jakub@redhat.com> wrote: > > > > > > On Tue, Sep 06, 2022 at 09:40:59AM +0200, Aldy Hernandez wrote: > > > > if (x <= Inf) > > > > > > This will be [-Inf, Inf] !NAN on the true side and > > > NAN (either sign) on the false side indeed. > > > > > > > if (x < -Inf) > > > > > > will be NAN (either sign) on the true side and > > > [-Inf, Inf] !NAN on the false side. > > > > Sweet, that's exactly what I thought, thus the patch. > > > > Furthermore, for !HONOR_NANS I would expect the NAN sides above to be > > UNDEFINED/unreachable. That is, the false side of x <= Inf when > > !HONOR_NANS is unreachable. > > In practice, there is no real format that has NaNs and doesn't have Infs > or vice versa and similarly we have just one switch to cover both Infinities > and NaNs, so either both are supported, or neither of them, or both > are supported but neither of them should appear in a valid program > (-ffinite-math-only on most floating point formats). > So the answer in that case is a little bit fuzzy because one shouldn't > compare against infinity in that case (or for !MODE_HAS_INFINITIES even > can't). But sure, if NaNs aren't possible or can't appear and you compare > x <= Largest_possible_float, then it is always true and so UNDEFINED on the > false edge. OK, let's leave it as undefined to be consistent. Come to think of it, perhaps we could represent the endpoints (varying, [x, +INF], etc) as the min/max representable values for the type (for !HONOR_NANS). I don't think it would make a big difference, but we might get better results for some corner cases. Question...for !HONOR_NANS or !HONOR_INFINITIES or whatever, say the range for the domain is [-MIN, +MAX] for the min and max representable numbers. What happens for MAX+1? Is that undefined? I wonder what real.cc does for that. Attached is the final version of the patch I'm pushing. Tested (+mpfr tests) on x86-64 Linux. Aldy [-- Attachment #2: 0001-Handle-INF-and-INF-correctly-in-range-op-float.cc.patch --] [-- Type: text/x-patch, Size: 6112 bytes --] From fd52ffb9997becafa31c5109b50fe274da12aed8 Mon Sep 17 00:00:00 2001 From: Aldy Hernandez <aldyh@redhat.com> Date: Tue, 6 Sep 2022 08:20:54 +0200 Subject: [PATCH] Handle > INF and < INF correctly in range-op-float.cc The gfortran.dg/minlocval*.f90 tests are generating conditionals past the infinities. For example: if (x <= +Inf) foo (x); else bar (x); It seems to me that the only possible value for x on the false side is either NAN or undefined (for !HONOR_NANS). gcc/ChangeLog: * range-op-float.cc (build_le): Handle NANs and going past infinity. (build_lt): Same. (build_ge): Same. (build_gt): Same. (foperator_lt::op1_range): Avoid adjustments to range if build_* returned false. (foperator_lt::op2_range): Same. (foperator_le::op1_range): Same. (foperator_le::op2_range): Same. (foperator_gt::op1_range): Same. (foperator_gt::op2_range): Same. gcc/testsuite/ChangeLog: * gcc.dg/tree-ssa/vrp-float-inf-1.c: New test. --- gcc/range-op-float.cc | 99 ++++++++++++++----- .../gcc.dg/tree-ssa/vrp-float-inf-1.c | 15 +++ 2 files changed, 90 insertions(+), 24 deletions(-) create mode 100644 gcc/testsuite/gcc.dg/tree-ssa/vrp-float-inf-1.c diff --git a/gcc/range-op-float.cc b/gcc/range-op-float.cc index 050f07a9867..5fbbaa1fb36 100644 --- a/gcc/range-op-float.cc +++ b/gcc/range-op-float.cc @@ -224,36 +224,79 @@ frange_drop_ninf (frange &r, tree type) // (X <= VAL) produces the range of [-INF, VAL]. -static void +static bool build_le (frange &r, tree type, const REAL_VALUE_TYPE &val) { + if (real_isnan (&val)) + { + r.set_undefined (); + return false; + } r.set (type, dconstninf, val); + return true; } // (X < VAL) produces the range of [-INF, VAL). -static void +static bool build_lt (frange &r, tree type, const REAL_VALUE_TYPE &val) { + if (real_isnan (&val)) + { + r.set_undefined (); + return false; + } + // < -INF is outside the range. + if (real_isinf (&val, 1)) + { + if (HONOR_NANS (type)) + frange_set_nan (r, type); + else + r.set_undefined (); + return false; + } // Hijack LE because we only support closed intervals. build_le (r, type, val); + return true; } // (X >= VAL) produces the range of [VAL, +INF]. -static void +static bool build_ge (frange &r, tree type, const REAL_VALUE_TYPE &val) { + if (real_isnan (&val)) + { + r.set_undefined (); + return false; + } r.set (type, val, dconstinf); + return true; } // (X > VAL) produces the range of (VAL, +INF]. -static void +static bool build_gt (frange &r, tree type, const REAL_VALUE_TYPE &val) { + if (real_isnan (&val)) + { + r.set_undefined (); + return false; + } + // > +INF is outside the range. + if (real_isinf (&val, 0)) + { + if (HONOR_NANS (type)) + frange_set_nan (r, type); + else + r.set_undefined (); + return false; + } + // Hijack GE because we only support closed intervals. build_ge (r, type, val); + return true; } @@ -520,10 +563,12 @@ foperator_lt::op1_range (frange &r, switch (get_bool_state (r, lhs, type)) { case BRS_TRUE: - build_lt (r, type, op2.upper_bound ()); - r.set_nan (fp_prop::NO); - // x < y implies x is not +INF. - frange_drop_inf (r, type); + if (build_lt (r, type, op2.upper_bound ())) + { + r.set_nan (fp_prop::NO); + // x < y implies x is not +INF. + frange_drop_inf (r, type); + } break; case BRS_FALSE: @@ -546,10 +591,12 @@ foperator_lt::op2_range (frange &r, switch (get_bool_state (r, lhs, type)) { case BRS_TRUE: - build_gt (r, type, op1.lower_bound ()); - r.set_nan (fp_prop::NO); - // x < y implies y is not -INF. - frange_drop_ninf (r, type); + if (build_gt (r, type, op1.lower_bound ())) + { + r.set_nan (fp_prop::NO); + // x < y implies y is not -INF. + frange_drop_ninf (r, type); + } break; case BRS_FALSE: @@ -618,8 +665,8 @@ foperator_le::op1_range (frange &r, switch (get_bool_state (r, lhs, type)) { case BRS_TRUE: - build_le (r, type, op2.upper_bound ()); - r.set_nan (fp_prop::NO); + if (build_le (r, type, op2.upper_bound ())) + r.set_nan (fp_prop::NO); break; case BRS_FALSE: @@ -642,8 +689,8 @@ foperator_le::op2_range (frange &r, switch (get_bool_state (r, lhs, type)) { case BRS_TRUE: - build_ge (r, type, op1.lower_bound ()); - r.set_nan (fp_prop::NO); + if (build_ge (r, type, op1.lower_bound ())) + r.set_nan (fp_prop::NO); break; case BRS_FALSE: @@ -712,10 +759,12 @@ foperator_gt::op1_range (frange &r, switch (get_bool_state (r, lhs, type)) { case BRS_TRUE: - build_gt (r, type, op2.lower_bound ()); - r.set_nan (fp_prop::NO); - // x > y implies x is not -INF. - frange_drop_ninf (r, type); + if (build_gt (r, type, op2.lower_bound ())) + { + r.set_nan (fp_prop::NO); + // x > y implies x is not -INF. + frange_drop_ninf (r, type); + } break; case BRS_FALSE: @@ -738,10 +787,12 @@ foperator_gt::op2_range (frange &r, switch (get_bool_state (r, lhs, type)) { case BRS_TRUE: - build_lt (r, type, op1.upper_bound ()); - r.set_nan (fp_prop::NO); - // x > y implies y is not +INF. - frange_drop_inf (r, type); + if (build_lt (r, type, op1.upper_bound ())) + { + r.set_nan (fp_prop::NO); + // x > y implies y is not +INF. + frange_drop_inf (r, type); + } break; case BRS_FALSE: diff --git a/gcc/testsuite/gcc.dg/tree-ssa/vrp-float-inf-1.c b/gcc/testsuite/gcc.dg/tree-ssa/vrp-float-inf-1.c new file mode 100644 index 00000000000..1d21cce41e6 --- /dev/null +++ b/gcc/testsuite/gcc.dg/tree-ssa/vrp-float-inf-1.c @@ -0,0 +1,15 @@ +// { dg-do compile } +// { dg-options "-O2 -fdump-tree-evrp-details" } + +void foo (); +void bar (double); + +void funky(double f, double g) +{ + if (f <= __builtin_inf ()) + foo (); + else + bar (f); +} + +// { dg-final { scan-tree-dump-not " Inf, Inf" "evrp" } } -- 2.37.1 ^ permalink raw reply [flat|nested] 11+ messages in thread

*Re: [PATCH] Handle > INF and < INF correctly in range-op-float.cc2022-09-06 11:47 ` Aldy Hernandez@ 2022-09-06 12:06 ` Jakub Jelinek2022-09-06 12:17 ` Richard Biener 2022-09-06 12:38 ` Koning, Paul 0 siblings, 2 replies; 11+ messages in thread From: Jakub Jelinek @ 2022-09-06 12:06 UTC (permalink / raw) To: Aldy Hernandez;+Cc:GCC patches, Richard Biener, Andrew MacLeod On Tue, Sep 06, 2022 at 01:47:43PM +0200, Aldy Hernandez wrote: > Question...for !HONOR_NANS or !HONOR_INFINITIES or whatever, say the > range for the domain is [-MIN, +MAX] for the min and max representable > numbers. What happens for MAX+1? Is that undefined? I wonder what > real.cc does for that. I'm afraid I have no idea. The formats without Inf/NaN are: spu_single_format vax_{f,d,g}_format arm_half_format Never had the "pleasure" to work with any of these. Looking at encode_vax_*, it seems both GCC internal inf and nan are most likely are encoded as maximum or minimum representable numbers (depending on sign), and encode_ieee_half for !fmt->has_inf does too (for !fmt->has_nans it seems to "encode" the nan mantissa bits into highest possible exponent). encode_ieee_single (for spu) uses maximum or minimum representable numbers for any infinities or nans. What they actually do at runtime is something I can't really check, but one would hope it is saturating... Jakub ^ permalink raw reply [flat|nested] 11+ messages in thread

*Re: [PATCH] Handle > INF and < INF correctly in range-op-float.cc2022-09-06 12:06 ` Jakub Jelinek@ 2022-09-06 12:17 ` Richard Biener2022-09-06 12:32 ` Aldy Hernandez 2022-09-06 12:38 ` Koning, Paul 1 sibling, 1 reply; 11+ messages in thread From: Richard Biener @ 2022-09-06 12:17 UTC (permalink / raw) To: Jakub Jelinek;+Cc:Aldy Hernandez, GCC patches, Andrew MacLeod On Tue, Sep 6, 2022 at 2:06 PM Jakub Jelinek <jakub@redhat.com> wrote: > > On Tue, Sep 06, 2022 at 01:47:43PM +0200, Aldy Hernandez wrote: > > Question...for !HONOR_NANS or !HONOR_INFINITIES or whatever, say the > > range for the domain is [-MIN, +MAX] for the min and max representable > > numbers. What happens for MAX+1? Is that undefined? I wonder what > > real.cc does for that. > > I'm afraid I have no idea. > > The formats without Inf/NaN are: > spu_single_format > vax_{f,d,g}_format > arm_half_format > > Never had the "pleasure" to work with any of these. > Looking at encode_vax_*, it seems both GCC internal inf and nan are > most likely are encoded as maximum or minimum representable numbers > (depending on sign), and encode_ieee_half for !fmt->has_inf does too > (for !fmt->has_nans it seems to "encode" the nan mantissa bits into > highest possible exponent). encode_ieee_single (for spu) uses > maximum or minimum representable numbers for any infinities or nans. > What they actually do at runtime is something I can't really check, > but one would hope it is saturating... I'd simply do what we do for -ffinite-math-only - just pretend you don't cross the maximum/minmum value and effectively saturate the range. Richard. > Jakub > ^ permalink raw reply [flat|nested] 11+ messages in thread

*Re: [PATCH] Handle > INF and < INF correctly in range-op-float.cc2022-09-06 12:17 ` Richard Biener@ 2022-09-06 12:32 ` Aldy Hernandez0 siblings, 0 replies; 11+ messages in thread From: Aldy Hernandez @ 2022-09-06 12:32 UTC (permalink / raw) To: Richard Biener;+Cc:Jakub Jelinek, GCC patches, Andrew MacLeod On Tue, Sep 6, 2022 at 2:17 PM Richard Biener <richard.guenther@gmail.com> wrote: > > On Tue, Sep 6, 2022 at 2:06 PM Jakub Jelinek <jakub@redhat.com> wrote: > > > > On Tue, Sep 06, 2022 at 01:47:43PM +0200, Aldy Hernandez wrote: > > > Question...for !HONOR_NANS or !HONOR_INFINITIES or whatever, say the > > > range for the domain is [-MIN, +MAX] for the min and max representable > > > numbers. What happens for MAX+1? Is that undefined? I wonder what > > > real.cc does for that. > > > > I'm afraid I have no idea. > > > > The formats without Inf/NaN are: > > spu_single_format > > vax_{f,d,g}_format > > arm_half_format > > > > Never had the "pleasure" to work with any of these. > > Looking at encode_vax_*, it seems both GCC internal inf and nan are > > most likely are encoded as maximum or minimum representable numbers > > (depending on sign), and encode_ieee_half for !fmt->has_inf does too > > (for !fmt->has_nans it seems to "encode" the nan mantissa bits into > > highest possible exponent). encode_ieee_single (for spu) uses > > maximum or minimum representable numbers for any infinities or nans. > > What they actually do at runtime is something I can't really check, > > but one would hope it is saturating... > > I'd simply do what we do for -ffinite-math-only - just pretend you don't > cross the maximum/minmum value and effectively saturate the range. Yeah, that sounds reasonable. I take it I can assume that MAX+1 is undefined for -ffinite-math-only? So I'm free to saturate, etc? Ok, crazy hypothetical talk... if (x > y) For -ffinite-math-only, on the true side, can I assume: x: MIN + 1 ULP y: MAX - 1 ULP range-op for integers did all sorts of stuff like that, and we ended up optimizing some interesting cases...as well as driving the middle end warnings crazy :-P. Aldy ^ permalink raw reply [flat|nested] 11+ messages in thread

*2022-09-06 12:06 ` Jakub Jelinek 2022-09-06 12:17 ` Richard BienerRe: [PATCH] Handle > INF and < INF correctly in range-op-float.cc@ 2022-09-06 12:38 ` Koning, Paul1 sibling, 0 replies; 11+ messages in thread From: Koning, Paul @ 2022-09-06 12:38 UTC (permalink / raw) To: Jakub Jelinek;+Cc:Aldy Hernandez, GCC Patches > On Sep 6, 2022, at 8:06 AM, Jakub Jelinek via Gcc-patches <gcc-patches@gcc.gnu.org> wrote: > > On Tue, Sep 06, 2022 at 01:47:43PM +0200, Aldy Hernandez wrote: >> Question...for !HONOR_NANS or !HONOR_INFINITIES or whatever, say the >> range for the domain is [-MIN, +MAX] for the min and max representable >> numbers. What happens for MAX+1? Is that undefined? I wonder what >> real.cc does for that. > > I'm afraid I have no idea. > > The formats without Inf/NaN are: > spu_single_format > vax_{f,d,g}_format > arm_half_format Actually, DEC (VAX and PDP-11) float does have NaN; signaling NaN to be precise. paul ^ permalink raw reply [flat|nested] 11+ messages in thread

end of thread, other threads:[~2022-09-06 12:38 UTC | newest]Thread overview:11+ messages (download: mbox.gz / follow: Atom feed) -- links below jump to the message on this page -- 2022-09-06 7:29 [PATCH] Handle > INF and < INF correctly in range-op-float.cc Aldy Hernandez 2022-09-06 7:35 ` Jakub Jelinek 2022-09-06 7:40 ` Aldy Hernandez 2022-09-06 7:44 ` Jakub Jelinek 2022-09-06 7:49 ` Aldy Hernandez 2022-09-06 7:59 ` Jakub Jelinek 2022-09-06 11:47 ` Aldy Hernandez 2022-09-06 12:06 ` Jakub Jelinek 2022-09-06 12:17 ` Richard Biener 2022-09-06 12:32 ` Aldy Hernandez 2022-09-06 12:38 ` Koning, Paul

This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).