Skip to main content

usual_arithmetic

Function usual_arithmetic 

Source
pub fn usual_arithmetic(
    types: &mut Types,
    left: TypeId,
    right: TypeId,
    target: &TargetInfo,
) -> Option<TypeId>
Expand description

The usual arithmetic conversions, 6.3.1.8: the one type both operands are converted to.

None when either operand is not an arithmetic type, which is not a failure of this function but the shape of a diagnostic its caller is about to write.

The floating rules come first and the integer rules only run when neither side is floating, which is why unsigned long long + float is float and loses precision rather than being the other way round.

The complexity comes off both operands first and goes back on at the end, which is 6.3.1.8p1 read literally: the rule is written over the corresponding real types and says the result is complex when either operand was. Doing it that way is also what gives gcc’s answer for the complex integer types, since _Complex int + long is the integer rule on int and long with the complexity carried across, and none of the integer rules had to learn the word.

A half of a complex operand is not promoted, which is measured from gcc 16.2.0 rather than read anywhere: _Complex char + _Complex char is a _Complex char where char + char is an int. The promotions are written over the integer types and a complex one is not one of them, so the operand that is not complex is promoted and the half is taken as it stands. _Complex char + char is therefore a _Complex int, since the char beside it promotes and the rule then picks the wider of the two.