[Cfp-interest] (SC22WG14.14282) TS 18661-3 and usual arithmetic conversions for long double, double

Jim Thomas jaswthomas at sbcglobal.net
Tue Jun 21 14:12:41 PDT 2016


Here are suggested words for filling in the missing specification in the unusual arithmetic conversions:

Replace:

Otherwise, if the corresponding real type of either operand is a standard floating type, the other operand is converted, without change of type domain, to a type whose corresponding real type is that same standard floating type.

with:
 
Otherwise, if the corresponding real type of either operand is long double, the other operand is converted, without change of type domain, to a type whose corresponding real type is long double.

Otherwise, if the corresponding real type of either operand is double, the other operand is converted, without change of type domain, to a type whose corresponding real type is double.

Otherwise, if the corresponding real type of either operand is _Float128x or _Decimal128x, the other operand is converted, without change of type domain, to a type whose corresponding real type is _Float128x or _Decimal128x, respectively.

Otherwise, if the corresponding real type of either operand is _Float64x or _Decimal64x, the other operand is converted, without change of type domain, to a type whose corresponding real type is _Float64x or _Decimal64x, respectively.

I like Joseph’s idea about having the tgmath specification refer to the usual arithmetic conversions. This could be done in Part 2 by replacing:

… use of a type-generic macro invokes a function whose generic parameters have the corresponding real type determined by the corresponding real types of the arguments as follows:

      … bullets

with:

… use of a type-generic macro invokes a function whose generic parameters have the corresponding real type determined by the types of the arguments for the generic parameters as follows:

-- Arguments of integer type are regarded as having type _Decimal64 if any argument has decimal floating type, and as having type double otherwise.

-- If the function has exactly one generic parameter, the type determined is the corresponding real type of the argument for the generic parameter.

-- If the function has exactly two generic parameters, the type determined is the corresponding real type determined by the usual arithmetic conversions (6.3.1.8) applied to the arguments for the generic parameters.

-- If the function has more than two generic parameters, the type determined is the corresponding real type determined by repeatedly applying the ususal arithmetic conversions, first to the first two arguments for generic parameters, then to that result type and the next argument for a generic parameter, and so forth until the usual arithmetic conversions have been applied to the last argument for a generic parameter.

I don’t think this would be a substantive change to Part 2.

The change would cover Part 3 too, so no change to the bullets that resolve the type would be needed there. As Joseph notes, the change would be substantive (though believed minor) for Part 3.

Maybe a better approach would be leave Part 2 alone and in Part 3 change the bullets to refer to the usual arithmetic conversions. Otherwise, the change in Part 3 would be dependent on the change in Part 2, which might cause confusion.

Jim Thomas

> On Jun 16, 2016, at 3:41 PM, Joseph Myers <joseph at codesourcery.com> wrote:
> 
> C11 specifies that the usual arithmetic conversions on the pair of types 
> (long double, double) produces a result of type long double.
> 
> Suppose long double and double have the same set of values.  TS 18661-3 
> rewrites the rules for usual arithmetic conversions so that the case "if 
> both operands are floating types and the sets of values of their 
> corresponding real types are equivalent" prefers interchange types to 
> standard types to extended types.  But this leaves the case of (long 
> double, double) unspecified as to which type is chosen, unlike in C11, as 
> those are both standard types.
> 
> I think this is a defect in TS 18661-3, and it should say that if both are 
> standard types with the same set of values then long double is preferred 
> to double which is preferred to float, as in C11.
> 
> A similar issue could arise if two of the extended types have equivalent 
> sets of values.  I'm not aware of anything to prohibit that, although it 
> seems less likely in practice.  I think the natural fix would be to say 
> that _Float128x is preferred to _Float64x which is preferred to _Float32x.
> 
> I think such an issue would also arise for <tgmath.h> (if _Float64x and 
> _Float128x have the same set of values, the choice doesn't seem to be 
> specified).  It also seems possible for the <tgmath.h> rules for purely 
> floating-point arguments to produce a different result from the usual 
> arithmetic conversions (consider the case where _Float32x is wider than 
> long double, and <tgmath.h> chooses long double), and since rules that are 
> the same in most cases but subtly different in obscure cases tend to be 
> confusing, I wonder if it might be better to specify much simpler rules 
> for <tgmath.h>: take the type resulting from the usual arithmetic 
> conversions[*], where integer arguments are replaced by _Decimal64 if 
> there are any decimal arguments and double otherwise.  (That's different 
> from the present rules for e.g. (_Float32x, int), but it's a lot simpler, 
> and seems unlikely in practice to choose a type with a different set of 
> values from the present choice.)
> 
> [*] Meaningful for more than two arguments as long as the usual arithmetic 
> conversions are commutative and associative as an operation on pairs of 
> types.
> 
> -- 
> Joseph S. Myers
> joseph at codesourcery.com

-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://mailman.oakapple.net/pipermail/cfp-interest/attachments/20160621/ec79f052/attachment-0001.html 


More information about the Cfp-interest mailing list