@@ -16,12 +16,6 @@ import cpp
1616import codingstandards.c.misra
1717import codingstandards.c.TgMath
1818
19- Expr getFullyExplicitlyConverted ( Expr e ) {
20- if e .hasExplicitConversion ( )
21- then result = getFullyExplicitlyConverted ( e .getExplicitlyConverted ( ) )
22- else result = e
23- }
24-
2519string argTypesString ( TgMathInvocation call , int i ) {
2620 exists ( string typeStr |
2721 typeStr = getEffectiveStandardType ( call .getOperandArgument ( i ) ) .toString ( ) and
@@ -33,12 +27,28 @@ string argTypesString(TgMathInvocation call, int i) {
3327 )
3428}
3529
36- predicate promotes ( Type type ) { type .( IntegralType ) .getSize ( ) < any ( IntType t ) .getSize ( ) }
37-
38- Type integerPromote ( Type type ) {
39- promotes ( type ) and result .( IntType ) .isSigned ( )
40- or
41- not promotes ( type ) and result = type
30+ /**
31+ * If the range of values can be represented as a signed int, it is promoted to signed int.
32+ *
33+ * A value may also promote to unsigned int but only if `int` cannot represent the range of
34+ * values. Which basically means only an `unsigned int` promotes to `unsigned int`, so we don't
35+ * need to do anything in this case.
36+ *
37+ * An unsigned int bitfield with fewer than 32 bits is promoted to `int`.
38+ */
39+ predicate promotesToSignedInt ( Expr e ) {
40+ exists ( int intBits , int intBytes |
41+ intBytes = any ( IntType t ) .getSize ( ) and
42+ intBits = intBytes * 8 and
43+ (
44+ e .( FieldAccess ) .getTarget ( ) .( BitField ) .getNumBits ( ) < intBits
45+ or
46+ e .getUnderlyingType ( ) .( IntegralType ) .getSize ( ) < intBytes
47+ )
48+ )
49+ }
50+ Type getPromotedType ( Expr e ) {
51+ if promotesToSignedInt ( e ) then result .( IntType ) .isSigned ( ) else result = e .getUnderlyingType ( )
4252}
4353
4454Type canonicalize ( Type type ) {
@@ -48,8 +58,7 @@ Type canonicalize(Type type) {
4858}
4959
5060Type getEffectiveStandardType ( Expr e ) {
51- result =
52- canonicalize ( integerPromote ( getFullyExplicitlyConverted ( e ) .getType ( ) .stripTopLevelSpecifiers ( ) ) )
61+ result = canonicalize ( getPromotedType ( e .getExplicitlyConverted ( ) ) )
5362}
5463
5564from TgMathInvocation call , Type firstType
0 commit comments