Skip to content

Commit e7a12ca

Browse files
committed
LangRef: Clarify llvm.minnum and llvm.maxnum about sNaN
The documents claims that it ignores sNaN, while in the code it may be different. - as the finally callback, it use libc call fmin(3)/fmax(3). while C23 clarify that fmin(3)/fmax(3) should return NaN for sNaN vs NUM. - on some architectures, such as aarch64, it converts to `fmaxnm`, which returns qNaN for sNaN vs NUM. - on RISC-V (SPEC 2019+), it converts to `fmax`, which returns NUM for sNaN vs NUM. Since we have introduced llvm.minimumnum and llvm.maximumnum, which follow IEEE 754-2019's minimumNumber/maximumNumber. So, it's time for use to clarify llvm.minnum and llvm.maxnum. Let's define it to the libc's defination.
1 parent 5d08625 commit e7a12ca

File tree

1 file changed

+31
-44
lines changed

1 file changed

+31
-44
lines changed

llvm/docs/LangRef.rst

Lines changed: 31 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -16464,21 +16464,13 @@ type.
1646416464

1646516465
Semantics:
1646616466
""""""""""
16467+
Follows the IEEE754 2008 semantics for minNum, except for handling of
16468+
+0.0 vs -0.0. This matches the behavior of libm's fmin.
1646716469

16468-
Follows the IEEE-754 semantics for minNum, except for handling of
16469-
signaling NaNs. This match's the behavior of libm's fmin.
16470-
16471-
If either operand is a NaN, returns the other non-NaN operand. Returns
16472-
NaN only if both operands are NaN. If the operands compare equal,
16473-
returns either one of the operands. For example, this means that
16474-
fmin(+0.0, -0.0) returns either operand.
16475-
16476-
Unlike the IEEE-754 2008 behavior, this does not distinguish between
16477-
signaling and quiet NaN inputs. If a target's implementation follows
16478-
the standard and returns a quiet NaN if either input is a signaling
16479-
NaN, the intrinsic lowering is responsible for quieting the inputs to
16480-
correctly return the non-NaN input (e.g. by using the equivalent of
16481-
``llvm.canonicalize``).
16470+
If either operand is a qNaN, returns the other non-NaN operand. Returns
16471+
NaN only if both operands are NaN or either operand is sNaN.
16472+
If the operands compare equal, returns either one of the operands.
16473+
For example, this means that fmin(+0.0, -0.0) returns either operand.
1648216474

1648316475
.. _i_maxnum:
1648416476

@@ -16515,20 +16507,13 @@ type.
1651516507

1651616508
Semantics:
1651716509
""""""""""
16518-
Follows the IEEE-754 semantics for maxNum except for the handling of
16519-
signaling NaNs. This matches the behavior of libm's fmax.
16510+
Follows the IEEE754 2008 semantics for maxNum, except for handling of
16511+
+0.0 vs -0.0. This matches the behavior of libm's fmax.
1652016512

1652116513
If either operand is a NaN, returns the other non-NaN operand. Returns
16522-
NaN only if both operands are NaN. If the operands compare equal,
16523-
returns either one of the operands. For example, this means that
16524-
fmax(+0.0, -0.0) returns either -0.0 or 0.0.
16525-
16526-
Unlike the IEEE-754 2008 behavior, this does not distinguish between
16527-
signaling and quiet NaN inputs. If a target's implementation follows
16528-
the standard and returns a quiet NaN if either input is a signaling
16529-
NaN, the intrinsic lowering is responsible for quieting the inputs to
16530-
correctly return the non-NaN input (e.g. by using the equivalent of
16531-
``llvm.canonicalize``).
16514+
NaN only if both operands are NaN or either operand is sNaN.
16515+
If the operands compare equal, returns either one of the operands.
16516+
For example, this means that fmin(+0.0, -0.0) returns either operand.
1653216517

1653316518
.. _i_minimum:
1653416519

@@ -19407,12 +19392,12 @@ The '``llvm.vector.reduce.fmax.*``' intrinsics do a floating-point
1940719392
matches the element-type of the vector input.
1940819393

1940919394
This instruction has the same comparison semantics as the '``llvm.maxnum.*``'
19410-
intrinsic. That is, the result will always be a number unless all elements of
19411-
the vector are NaN. For a vector with maximum element magnitude 0.0 and
19412-
containing both +0.0 and -0.0 elements, the sign of the result is unspecified.
19395+
intrinsic. If the intrinsic call has the ``nnan`` fast-math flag, then the
19396+
operation can assume that NaNs are not present in the input vector.
1941319397

19414-
If the intrinsic call has the ``nnan`` fast-math flag, then the operation can
19415-
assume that NaNs are not present in the input vector.
19398+
It is deprecated, since the different order of inputs may produce different
19399+
outputs, and it is hard to optimize with Vector or SIMD extensions.
19400+
Use '``llvm.vector.reduce.fmaximum``' or '``llvm.vector.reduce.fmaximumnum``' instead.
1941619401

1941719402
Arguments:
1941819403
""""""""""
@@ -19440,12 +19425,12 @@ The '``llvm.vector.reduce.fmin.*``' intrinsics do a floating-point
1944019425
matches the element-type of the vector input.
1944119426

1944219427
This instruction has the same comparison semantics as the '``llvm.minnum.*``'
19443-
intrinsic. That is, the result will always be a number unless all elements of
19444-
the vector are NaN. For a vector with minimum element magnitude 0.0 and
19445-
containing both +0.0 and -0.0 elements, the sign of the result is unspecified.
19428+
intrinsic. If the intrinsic call has the ``nnan`` fast-math flag, then the
19429+
operation can assume that NaNs are not present in the input vector.
1944619430

19447-
If the intrinsic call has the ``nnan`` fast-math flag, then the operation can
19448-
assume that NaNs are not present in the input vector.
19431+
It is deprecated, since the different order of inputs may produce different
19432+
outputs, and it is hard to optimize with Vector or SIMD extensions.
19433+
Use '``llvm.vector.reduce.fminimum``' or '``llvm.vector.reduce.fminimumnum``' instead.
1944919434

1945019435
Arguments:
1945119436
""""""""""
@@ -22994,13 +22979,14 @@ result type. If only ``nnan`` is set then the neutral value is ``-Infinity``.
2299422979

2299522980
This instruction has the same comparison semantics as the
2299622981
:ref:`llvm.vector.reduce.fmax <int_vector_reduce_fmax>` intrinsic (and thus the
22997-
'``llvm.maxnum.*``' intrinsic). That is, the result will always be a number
22998-
unless all elements of the vector and the starting value are ``NaN``. For a
22999-
vector with maximum element magnitude ``0.0`` and containing both ``+0.0`` and
23000-
``-0.0`` elements, the sign of the result is unspecified.
22982+
'``llvm.maxnum.*``' intrinsic).
2300122983

2300222984
To ignore the start value, the neutral value can be used.
2300322985

22986+
It is deprecated, since the different order of inputs may produce different
22987+
outputs, and it is hard to optimize with Vector or SIMD extensions.
22988+
Use '``llvm.vp.vector.reduce.fmaximum``' or '``llvm.vp.vector.reduce.fmaximumnum``' instead.
22989+
2300422990
Examples:
2300522991
"""""""""
2300622992

@@ -23064,13 +23050,14 @@ result type. If only ``nnan`` is set then the neutral value is ``+Infinity``.
2306423050

2306523051
This instruction has the same comparison semantics as the
2306623052
:ref:`llvm.vector.reduce.fmin <int_vector_reduce_fmin>` intrinsic (and thus the
23067-
'``llvm.minnum.*``' intrinsic). That is, the result will always be a number
23068-
unless all elements of the vector and the starting value are ``NaN``. For a
23069-
vector with maximum element magnitude ``0.0`` and containing both ``+0.0`` and
23070-
``-0.0`` elements, the sign of the result is unspecified.
23053+
'``llvm.minnum.*``' intrinsic).
2307123054

2307223055
To ignore the start value, the neutral value can be used.
2307323056

23057+
It is deprecated, since the different order of inputs may produce different
23058+
outputs, and it is hard to optimize with Vector or SIMD extensions.
23059+
Use '``llvm.vp.vector.reduce.fminimum``' or '``llvm.vp.vector.reduce.fminimumnum``' instead.
23060+
2307423061
Examples:
2307523062
"""""""""
2307623063

0 commit comments

Comments
 (0)