Draft 754R Minutes - 29 December 2017 Recorded by David Hough Also at: http://754r.ucbtest.org/minutes/2017-12-29-minutes.txt The 754R revision group met by teleconference on 29 December 2017: convened at 8:00am and adjourned at 09:40am Pacific Standard Time. Teleconference participants: David Chen AlayaTec Jim Demmel UC Berkeley David Gay AMPL Optimization Roger Golliver unaffiliated Michel Hack IBM David Hough unaffiliated Ivan Godard Mill Computing Terje Mathisen Mill Computing Rich Painter unaffiliated Jim Thomas unaffiliated Leonard Tsai unaffiliated Lee Winter unaffiliated The IEEE-SA slides were referred to; the URL is: https://development.standards.ieee.org/myproject/Public/mytools/mob/slideset.pdf Officers: A request for volunteers to serve as vice-chair and secretary was met with deafening silence. Meetings: Teleconference-only meetings are scheduled for Friday 19 January, 9 February, 2 March, 8:00-10:00 am Pacific Time. Mailing list: Anybody may subscribe to the mailing list; send any email to: STDS-754-subscribe-request@LISTSERV.IEEE.ORG Website: Website is http://754r.ucbtest.org ================== Topics: ===== non-canonical encodings - draft 2.29 2.1.8 canonical encoding: The preferred encoding of a floating-point representation in a format. Applied to declets, significands of finite numbers, infinities, and NaNs, especially in decimal formats. 2.1.13 declet: An encoding of three decimal digits into ten bits using the densely packed decimal encoding scheme. Of the 1024 possible declets, 1000 canonical declets are produced by computational operations, while 24 non-canonical declets are not produced by computational operations, but are accepted in operands. 3.5.2: A NaN is in its preferred (canonical) encoding if the bits G6 through Gw + 4 are zero and the encoding of the payload is canonical. The two canonical encodings of infinity have bits G5 through Gw +4 = 0, and T = 0. [decimal encoding number] A canonical significand has only canonical declets, as shown in Tables 3.3 and 3.4. Computational operations produce only the 1000 canonical declets, but also accept the 24 non-canonical declets in operands. [binary encoding number] If the value exceeds the maximum, the significand c is non-canonical and the value used for c is zero. Computational operations generally produce only canonical significands, and always accept non-canonical significands in operands. The 24 non-canonical patterns of the form 01x11x111x, 10x11x111x, or 11x11x111x (where an "x" denotes a "don't care" bit) are not generated in the result of a computational operation. However, as listed in Table 3.3, these 24 bit patterns do map to values in the range 0 through 999. The bit pattern in a NaN trailing significand field can affect how the NaN is propagated (see 6.2). 5.3.1: these operations shall not propagate non-canonical encodings (even when they return the value of an operand) 5.3.2, 5.3.3, 5.4.1, 5.4.2, 5.4.3, 9.2, 9.4, 9.5, 9.6, 9.7: operations shall not propagate non-canonical encodings 5.5.1, 5.5.2, sign bit and decimal re-encoding operations: These operations may propagate non-canonical encodings. 5.7.2: isCanonical(x) is true if and only if x is a finite number, infinity, or NaN that is canonical. Implementations should extend isCanonical(x) to formats that are not interchange formats in ways appropriate to those formats, which might, or might not, have finite numbers, infinities, or NaNs that are non-canonical. 5.10: totalOrder(x, y) imposes a total ordering on canonical members of the format of x and y For canonical x and y, totalOrder(x, y) and totalOrder( y, x) are both true if x and y are bitwise identical. NOTE - totalOrder does not impose a total ordering on all encodings in a format. In particular, it does not distinguish among different encodings of the same floating-point representation, as when one or both encodings are non-canonical. 5.12.2: Conversions from a supported decimal format df to an external character sequence and back again results in a canonical copy of the original number so long as the conversion to the external character sequence is one that preserves the quantum. 6.2: If the trailing significand field of a decimal input NaN is canonical then the bit pattern of that field shall be preserved if that NaN is chosen as the result NaN. 6.2.2: Any computational operation that produces, propagates, or quiets a decimal format NaN shall set the bits G6 through Gw + 4 of G to 0, and shall generate only a canonical trailing significand field. 6.2.3: Conversion of a quiet NaN from a narrower format to a wider format in the same radix, and then back to the same narrower format, should not change the quiet NaN payload in any way except to make it canonical. B.4: In formats with superfluous bit patterns not generated by arithmetic, such as non-canonical significand fields in decimal formats, debuggers should be able to enable signaling-NaN behavior for data containing such bit patterns. ==== non-canonical encodings - observations and questions It's pretty difficult to figure out all the ramifications of non-canonical encodings. I was willing to let that slide as long as binary interchange formats were strictly canonical. But now that we allow non-canonical binary interchange NaNs - a major mistake for which I expect we shall receive no thanks whatever from surprised application writers and end users - I have a SUGGESTION: Add section 3.8 Non-canonical encodings: Except for 5.5.1 sign bit operations and 5.5.2 re-encoding operations which specify otherwise, non-canonical operands are converted to canonical form before an operation, and operation results are canonical. A particular format might have non-canonical encodings for numbers or NaNs or both: * For 3.4 binary interchange formats: there are only canonical encodings of numbers; an implementation might define some NaN encodings to be non-canonical by defining its mapping of non-canonical to canonical encodings. * For 3.5 decimal interchange formats: there are non-canonical encodings of numbers, with a standard mapping to canonical encodings defined in 3.5.2. there are non-canonical encodings of NaNs, with a standard mapping to canonical encodings defined in 3.5.2. * For all other binary and decimal formats, an implementation might define some number or NaN encodings, or both, to be non-canonical, by defining its mapping of non-canonical to canonical encodings. Discussion: consensus agreement that all binary interchange format encodings are canonical. So no need for a section 3.8. Instead, == ACTION ITEM EDITOR: add one sentence to 3.4, perhaps before the NOTE: In binary interchange formats, all number and NaN encodings are canonical. == That leaves non-interchange formats. We adopted Jim Thomas' suggestion as a starting point: == ACTION ITEM EDITOR: In 3.7, change Any encodings for these formats are implementation-defined, but should be fixed width and may match those of an interchange format. Each NaN in these formats has a payload which may encode diagnostic information. to Encodings in these formats should be fixed width and may match those of an interchange format. Each representation of a floating-point number has a unique canonical encoding and may have non-canonical encodings. Each NaN in these formats has a payload which may encode diagnostic information. Each NaN payload has a canonical encoding and may have non-canonical encodings. Otherwise, encodings for these formats are implementation defined. == This introduces a new idea of canonical encodings of payloads. Hough prefers: == FUTURE AGENDA ITEM: Change Each representation of a floating-point number has a unique canonical encoding and may have non-canonical encodings. Each NaN in these formats has a payload which may encode diagnostic information. Each NaN payload has a canonical encoding and may have non-canonical encodings. to Each representation of a floating-point number or a NaN has a unique canonical encoding and may have non-canonical encodings. Each NaN in these formats has a payload which may encode diagnostic information. == ===== payload - draft 2.29 2.1.41 payload: The diagnostic information contained in a NaN, encoded in part of its trailing significand field. 3.5.2 decimal interchange format encodings T is the NaN's payload, which can be used to distinguish various NaNs. The NaN payload is encoded similarly to finite numbers described below, with G treated as though all bits were zero. The payload corresponds to the significand of finite numbers, interpreted as an integer with a maximum value of 10^ (3xJ) - 1, and the exponent field is ignored (it is treated as if it were zero). A NaN is in its preferred (canonical) encoding if the bits G6 through Gw + 4 are zero and the encoding of the payload is canonical. The maximum value of the binary-encoded significand is the same as that of the corresponding decimal-encoded significand; that is, 10^(3xJ + 1) -1 (or 10^(3xJ ) -1 when T is used as the payload of a NaN). 3.7: Extended and extendable Each NaN in these formats has a payload which may encode diagnostic information. 5.12.1: Language standards should provide an optional conversion of NaNs in a supported format to external character sequences which appends to the basic NaN character sequences a suffix that can represent the NaN payload. The form and interpretation of the payload suffix is language-defined. 6.2.1: binary Bits d2 d3 ... dp-1 of the trailing significand field contain the encoding of the payload, which might be diagnostic information. [??? What about non-interchange formats - which might not use a trailing significand field for NaNs] 6.2.2: decimal For decimal formats, the payload is the trailing significand field, as defined in 3.5. [??? What about non-interchange formats - which might not use a trailing significand field for NaNs] 6.2.3 NaN propagation An operation that propagates a NaN operand to its result and has a single NaN as an input should produce a NaN with the payload of the input NaN if representable in the destination format. If two or more inputs are NaN, then the payload of the resulting NaN should be identical to the payload of one of the input NaNs if representable in the destination format. This standard does not specify which of the input NaNs will provide the payload. Conversion of a quiet NaN from a narrower format to a wider format in the same radix, and then back to the same narrower format, should not change the quiet NaN payload in any way except to make it canonical. Conversion of a quiet NaN to a floating-point format of the same or a different radix that does not allow the payload to be preserved, shall return a quiet NaN that should provide some language-defined diagnostic information. There should be means to read and write payloads from and to external character sequences. 9.7 NaN payload operations Language standards should define the following homogeneous quiet-computational operations to provide generic access to NaN payloads. These operations signal no exceptions. These operations do not propagate non-canonical encodings. - sourceFormat getPayload(source) If the source operand is a NaN, the result is the NaN's payload as a non-negative floating-point integer. If the source operand is not a NaN, the result is -1. The preferred exponent is 0. - sourceFormat setPayload(source) If the source operand is a non-negative floating-point integer whose value is one of an implementation-defined set of admissible payloads for the operation, the result is a quiet NaN with that payload. Otherwise, the result is +0, with a preferred exponent of 0. - sourceFormat setPayloadSignaling(source) If the source operand is a non-negative floating-point integer whose value is one of an implementation-defined set of admissible payloads for the operation, the result is a signaling NaN with that payload. Otherwise, the result is +0, with a preferred exponent of 0. NOTE - An implementation may restrict the payloads that can be set by the user. Thus getPayload might return a value that is not an admissible operand for setPayload or setPayloadSignaling. (A program can check by applying the isNaN operation to the result of setPayload or setPayloadSignaling.) 10.4: The following value-changing transformations, among others, preserve the literal meaning of the source code: - Changing the payload or sign bit of a quiet NaN. Users obtain the same floating-point numerical and reproducible status flag results, on all platforms supporting such a language standard, by writing programs that: - Do not depend on quiet NaN propagation, payloads, or sign bits. B.3: By default, even a subprogram presumed to be debugged should at least insert a reference to its name in a status flag and in the payload of any new quiet NaN produced as a floating-point result of an invalid operation. These references indicate the origin of the exception or NaN. Debuggers should be able to maintain tables of histories of quiet NaNs, using the NaN payload to index the tables. ===== payload observations and questions For binary interchange formats, we pay a heavy price for defining the payload as other than the trailing significand - a burden of considering non-canonical representations. On the other hand, that burden was due in any case for non-interchange formats. Glossary: In non-interchange formats, the NaN payload might not be encoded in a trailing significand field - there might be only one quiet and one signaling NaN. SUGGESTION: Change 2.1.41 payload: The diagnostic information contained in a NaN, encoded in part of its trailing significand field. to 2.1.41 payload: The diagnostic information contained in a NaN. For binary interchange formats, the payload is encoded in part of its trailing significand field. For decimal interchange formats, the payload is the trailing significand field. Discussion: too much information in glossary, and "part of" is misleading for decimal interchange formats. == ACTION ITEM EDITOR: Change 2.1.41 payload: The diagnostic information contained in a NaN, encoded in part of its trailing significand field. to 2.1.41 payload: The diagnostic information contained in a NaN. == I think "user" is the not really what's meant in the NOTE. Omitted by mistake. == FUTURE AGENDA ITEM: Change NOTE - An implementation may restrict the payloads that can be set by the user. to NOTE - An implementation may restrict the payloads that can be set by application software. == ===== Decimal re-encoding operations - draft 2.29 For each supported decimal format (if any), the implementation shall provide the following operations to convert between the decimal format and the two standard encodings for that format. These operations enable portable programs that are independent of the implementation's encoding for decimal formats to access data represented with either standard encoding. These operations may propagate non-canonical encodings. - decimalEncoding encodeDecimal(decimal) Encodes the value of the operand using decimal encoding. - decimal decodeDecimal(decimalEncoding) Decodes the decimal-encoded operand. - binaryEncoding encodeBinary(decimal) Encodes the value of the operand using the binary encoding. - decimal decodeBinary(binaryEncoding) Decodes the binary-encoded operand. ===== re-encoding observations and questions Is anybody aware of an application that used these operations, in the ten years since 2008 was published? Or any application at all that was intended to run on both decimal significand encodings without knowing which one? These operations have the unusual property that they might be no-ops, or might not. A more economical approach would have been to define just two operations, binary-to-decimal and decimal-to-binary. It seems far more likely to me that an application intending to share data between implementations with different decimal significand encodings would do so in character strings. SUGGESTION #1: remove these operations from 2018 as not of general enough interest to warrant mandatory implementation Not accepted. == Aside from decimal interchange formats, we know nothing about decimal significand encodings that might be in use, and so would not expect to share data from non-interchange formats between implementations, except as character strings. SUGGESTION #2: Change For each supported decimal format (if any), the implementation shall provide... to Implementations supporting decimal interchange formats, shall provide, for each supported decimal interchange format, ... ACTION ITEM EDITOR: Change For each supported decimal format (if any), to For each supported decimal interchange format, == Why the uncertainty about canonical results if the operations are not no-ops? == ACTION ITEM EDITOR: Change These operations may propagate non-canonical encodings. to If the significand encoding of the result format is the same as the significand encoding of the operand format, then these operations should be copy operations. If the significand encoding of the result format is different from the significand encoding of the operand format, then the result should be be canonical. == "should be" instead of "shall" because it represents a slight tightening that might conceivably affect an existing implementation. Suggestion to have just two operations, explicitly between decimal and binary and vice versa, rejected. Suggestion to have an explicit canonicalize operation rejected. There is no operation currently that canonicalizes numbers and NaNs with no other semantics. ==== totalOrder - draft 2.29 5.7.2: Implementations shall provide the following non-computational operations for all supported arithmetic formats and should provide them for all supported interchange formats. They are never exceptional, even for signaling NaNs. boolean totalOrder(source, source) totalOrder(x, y) is defined in 5.10. boolean totalOrderMag(source, source) totalOrderMag(x, y) is totalOrder(abs(x), abs(y)). 5.10: For each supported arithmetic format, an implementation shall provide the following predicate that defines an ordering among all operands in a particular format: boolean totalOrder(source, source) totalOrder(x, y) imposes a total ordering on canonical members of the format of x and y: a)If x < y, totalOrder(x, y) is true. b)If x > y, totalOrder(x, y) is false. c)If x = y: 1)totalOrder(?0, +0) is true. 2)totalOrder(+0, ?0) is false. 3)If x and y represent the same floating-point datum: i)If x and y have negative sign, totalOrder(x, y) is true if and only if the exponent of x >= the exponent of y ii)otherwise totalOrder(x, y) is true if and only if the exponent of x <= the exponent of y. d)If x and y are unordered numerically because x or y is a NaN: 1)totalOrder(-NaN, y) is true where -NaN represents a NaN with negative sign bit and y is a floating-point number. 2)totalOrder(x, +NaN) is true where +NaN represents a NaN with positive sign bit and x is a floating-point number. 3)If x and y are both NaNs, then totalOrder reflects a total ordering based on: i)negative sign orders below positive sign ii)signaling orders below quiet for +NaN, reverse for -NaN iii)lesser payload, when regarded as an integer, orders below greater payload for +NaN, reverse for -NaN. Neither signaling NaNs nor quiet NaNs signal an exception. For canonical x and y, totalOrder(x, y) and totalOrder( y, x) are both true if x and y are bitwise identical. NOTE - totalOrder does not impose a total ordering on all encodings in a format. In particular, it does not distinguish among different encodings of the same floating-point representation, as when one or both encodings are non-canonical. 6.3: The logical predicates totalOrder and isSignMinus are also affected by the sign bit of a NaN operand. ===== totalOrder observations and questions SUGGESTION #1: remove totalOrder from 2018 restore it in 2028 if we can agree on what's needed Rejected. totalOrderMag(x, y) is totalOrder(abs(x), abs(y)). [mathematical abs or operation abs? "abs" not bolded in 2.29] SUGGESTION #2: In the definition, totalOrderMag(x, y) is totalOrder(abs(x), abs(y)) bold the occurrences of "abs" to make clear that they refer to the standard operation. = ACTION ITEM EDITOR: bold abs in totalOrderMag(x, y) is totalOrder(abs(x), abs(y)) == By consensus, retained existing definition of totalOrder with possible minor tweaks. "lesser payload, when regarded as an integer" is a red herring. == FUTURE AGENDA ITEM: Change iii)lesser payload, when regarded as an integer, orders below greater payload for +NaN, reverse for -NaN. to iii) within each NaN class -SNan, -QNaN, +QNaN, or +SNaN, ordering of canonical encodings is implementation-defined. == == FUTURE AGENDA ITEM: Change totalOrder does not impose a total ordering on all encodings in a format. In particular, it does not distinguish among different encodings of the same floating-point representation, as when one or both encodings are non-canonical. to If x or y are non-canonical and X and Y are the corresponding canonical encodings, then totalOrder(x,y) is totalOrder(X,Y). Thus totalOrder does not impose a total ordering on all encodings in a format. == Non-canonical encodings can no longer be ignored as rare, even in binary interchange formats, since we now acknowledge that binary interchange NaNs can be non-canonical and implementation-dependent, so it is possible to export a canonical NaN in a binary file and import it on a different system as non-canonical. So totalOrder ought to deal with non-canonical encodings. Numbers: Which of the following is most useful with respect to numbers in formats other than binary interchange?: no standard-imposed ordering of non-canonical with respect to anything or non-canonical ordered equal to canonical or non-canonical ordered somehow with respect to canonical NaNs: "payload when regarded as an integer" requires explanation. "as a non-negative floating-point integer" is the phrase used in the payload function description; if totalOrder is going to order according to payload, then it should (forward) reference the getPayload operation rather than half-reinvent it. The trailing significand field can be regarded as an integer, and the encoded payload within the trailing significand field can be regarded as an integer, but that might not coincide with the encoded or decoded payload. The decoded payload might be a pointer into a table that contains diagnostic information, not necessarily in the form of an integer. Non-interchange formats might not use a trailing significand field for NaNs. Which of the following is most useful with respect to NaNs?: -NaN < number < +NaN with no standard-imposed ordering of quiet/signaling/payload/non-canonical. all binary interchange formats can be fast -SNaN < -QNaN < number < +QNaN < +SNaN with no standard-imposed ordering of payload/non-canonical. most binary interchange formats can be fast -SNaN < -QNaN < number < +QNaN < +SNaN ordered within NaN groups according to trailing significand field with no standard-imposed ordering of non-canonical. most binary interchange formats can be fast -SNaN < -QNaN < number < +QNaN < +SNaN ordered within NaN groups according to decoded payload with no standard-imposed ordering of non-canonical. -SNaN < -QNaN < number < +QNaN < +SNaN ordered within NaN groups according to decoded payload with non-canonical ordered same as canonical -SNaN < -QNaN < number < +QNaN < +SNaN ordered within NaN groups according to decoded payload with non-canonical ordered somehow with respect to canonical SUGGESTION #3: definition proposed last month: For binary interchange formats, totalOrder(x, y) imposes a total ordering on all members of the format of x and y by defining totalOrder(x,y) to be the result of comparing x and y as sign-magnitude integers. Thus: a) if x and y are bitwise identical, then totalOrder(x,y) and totalOrder(y,x) are both true; b) otherwise one of totalOrder(x,y) and totalOrder(y,x) is true and the other false; c) for numbers and infinities, totalOrder(x,y) if and only if x<=y. d) representable entities are ordered: 1) NaNs with negative sign bit 2) infinities with negative sign bit 3) normal numbers with negative sign bit 4) subnormal numbers with negative sign bit 5) zero numbers with negative sign bit 6) zero numbers with positive sign bit 7) subnormal numbers with positive sign bit 8) normal numbers with positive sign bit 9) infinities with positive sign bit 10) NaNs with positive sign bit For all other formats, totalOrder(x, y) imposes a total ordering on canonical members of the format of x and y, preserving properties abcd) above, and adding e) numbers with positive sign bit that are numerically equal but not bitwise identical because of different exponent fields are ordered according to increasing exponent; numbers with negative sign bit that are numerically equal but not bitwise identical because of different exponent fields are ordered according to decreasing exponent. If x or y is non-canonical, then consider the corresponding canonical encodings X and Y. a) If X and Y are not bitwise identical, then totalOrder(x,y) is the same as totalOrder(X,Y), and thus just one of totalOrder(X,Y) or totalOrder(Y,X) is true. b) If X and Y are bitwise identical, then it is implementation defined whether 1) totalOrder(x,y) and totalOrder(y,x) are both true, or 2) just one of totalOrder(x,y) or totalOrder(y,x) is true. Thus in a format with non-canonical encodings, totalOrder might not impose a total ordering on all encodings in that format. For all formats, order of NaNs is implementation-defined. Neither signaling nor quiet NaN operands signal an exception. Rejected. SUGGESTION #4: definition proposed last month, expanded to separate signaling and quiet NaNs: totalOrder(x, y) imposes a total ordering on canonical members of the format of x and y, such that: a) if x and y are bitwise identical, then totalOrder(x,y) and totalOrder(y,x) are both true; b) otherwise one of totalOrder(x,y) and totalOrder(y,x) is true and the other false; c) for numbers and infinities, totalOrder(x,y) if and only if x<=y. d) representable entities are ordered: 0) signaling NaNs with negative sign bit 1) quiet NaNs with negative sign bit 2) infinities with negative sign bit 3) normal numbers with negative sign bit 4) subnormal numbers with negative sign bit 5) zero numbers with negative sign bit 6) zero numbers with positive sign bit 7) subnormal numbers with positive sign bit 8) normal numbers with positive sign bit 9) infinities with positive sign bit 10) quiet NaNs with positive sign bit 11) signaling NaNs with positive sign bit e) numbers with positive sign bit that are numerically equal but not bitwise identical because of different exponent fields are ordered according to increasing exponent; numbers with negative sign bit that are numerically equal but not bitwise identical because of different exponent fields are ordered according to decreasing exponent. If x or y is non-canonical, then consider the corresponding canonical encodings X and Y. a) If X and Y are not bitwise identical, then totalOrder(x,y) is the same as totalOrder(X,Y), and thus just one of totalOrder(X,Y) or totalOrder(Y,X) is true. b) If X and Y are bitwise identical, then it is implementation defined whether 1) totalOrder(x,y) and totalOrder(y,x) are both true, or 2) just one of totalOrder(x,y) or totalOrder(y,x) is true. Thus in a format with non-canonical encodings, totalOrder might not impose a total ordering on all encodings in that format. For all formats, order of signaling and quiet NaNs is implementation-defined. Neither signaling nor quiet NaN operands signal an exception. Rejected. ===== SUGGESTION: Define the NaN payload of a binary interchange format to be the trailing significand except the leading bit, analogous to decimal interchange format. Rejected.