@@ -92,8 +92,9 @@ class Type extends Locatable, @type {
9292 /**
9393 * Gets this type after typedefs have been resolved.
9494 *
95- * The result of this predicate will be the type itself, except in the case of a TypedefType or a Decltype,
96- * in which case the result will be type which results from (possibly recursively) resolving typedefs.
95+ * The result of this predicate will be the type itself, except in the case of a TypedefType, a Decltype,
96+ * or a TypeofType, in which case the result will be type which results from (possibly recursively)
97+ * resolving typedefs.
9798 */
9899 pragma [ nomagic]
99100 Type getUnderlyingType ( ) { result = this }
@@ -1117,18 +1118,20 @@ class DerivedType extends Type, @derivedtype {
11171118 * decltype(a) b;
11181119 * ```
11191120 */
1120- class Decltype extends Type , @decltype {
1121+ class Decltype extends Type {
1122+ Decltype ( ) { decltypes ( underlyingElement ( this ) , _, 0 , _, _) }
1123+
11211124 override string getAPrimaryQlClass ( ) { result = "Decltype" }
11221125
11231126 /**
1124- * The expression whose type is being obtained by this decltype.
1127+ * Gets the expression whose type is being obtained by this decltype.
11251128 */
1126- Expr getExpr ( ) { decltypes ( underlyingElement ( this ) , unresolveElement ( result ) , _, _) }
1129+ Expr getExpr ( ) { decltypes ( underlyingElement ( this ) , unresolveElement ( result ) , _, _, _ ) }
11271130
11281131 /**
1129- * The type immediately yielded by this decltype.
1132+ * Gets the type immediately yielded by this decltype.
11301133 */
1131- Type getBaseType ( ) { decltypes ( underlyingElement ( this ) , _, unresolveElement ( result ) , _) }
1134+ Type getBaseType ( ) { decltypes ( underlyingElement ( this ) , _, _ , unresolveElement ( result ) , _) }
11321135
11331136 /**
11341137 * Whether an extra pair of parentheses around the expression would change the semantics of this decltype.
@@ -1142,7 +1145,7 @@ class Decltype extends Type, @decltype {
11421145 * ```
11431146 * Please consult the C++11 standard for more details.
11441147 */
1145- predicate parenthesesWouldChangeMeaning ( ) { decltypes ( underlyingElement ( this ) , _, _, true ) }
1148+ predicate parenthesesWouldChangeMeaning ( ) { decltypes ( underlyingElement ( this ) , _, _, _ , true ) }
11461149
11471150 override Type getUnderlyingType ( ) { result = this .getBaseType ( ) .getUnderlyingType ( ) }
11481151
@@ -1183,6 +1186,215 @@ class Decltype extends Type, @decltype {
11831186 }
11841187}
11851188
1189+ /**
1190+ * An instance of the C23 `typeof` or `typeof_unqual` operator. For example:
1191+ * ```
1192+ * int a;
1193+ * typeof(a) b;
1194+ * typeof_unqual(const int) b;
1195+ * ```
1196+ */
1197+ class TypeofType extends Type {
1198+ TypeofType ( ) {
1199+ decltypes ( underlyingElement ( this ) , _, 1 , _, _) or
1200+ type_operators ( underlyingElement ( this ) , _, 0 , _)
1201+ }
1202+
1203+ /**
1204+ * Gets the type immediately yielded by this typeof.
1205+ */
1206+ Type getBaseType ( ) {
1207+ decltypes ( underlyingElement ( this ) , _, _, unresolveElement ( result ) , _)
1208+ or
1209+ type_operators ( underlyingElement ( this ) , _, _, unresolveElement ( result ) )
1210+ }
1211+
1212+ override Type getUnderlyingType ( ) { result = this .getBaseType ( ) .getUnderlyingType ( ) }
1213+
1214+ override Type stripTopLevelSpecifiers ( ) { result = this .getBaseType ( ) .stripTopLevelSpecifiers ( ) }
1215+
1216+ override Type stripType ( ) { result = this .getBaseType ( ) .stripType ( ) }
1217+
1218+ override Type resolveTypedefs ( ) { result = this .getBaseType ( ) .resolveTypedefs ( ) }
1219+
1220+ override string toString ( ) { result = "typeof(...)" }
1221+
1222+ override string getName ( ) { none ( ) }
1223+
1224+ override int getSize ( ) { result = this .getBaseType ( ) .getSize ( ) }
1225+
1226+ override int getAlignment ( ) { result = this .getBaseType ( ) .getAlignment ( ) }
1227+
1228+ override int getPointerIndirectionLevel ( ) {
1229+ result = this .getBaseType ( ) .getPointerIndirectionLevel ( )
1230+ }
1231+
1232+ override string explain ( ) {
1233+ result = "typeof resulting in {" + this .getBaseType ( ) .explain ( ) + "}"
1234+ }
1235+
1236+ override predicate involvesReference ( ) { this .getBaseType ( ) .involvesReference ( ) }
1237+
1238+ override predicate involvesTemplateParameter ( ) { this .getBaseType ( ) .involvesTemplateParameter ( ) }
1239+
1240+ override predicate isDeeplyConst ( ) { this .getBaseType ( ) .isDeeplyConst ( ) }
1241+
1242+ override predicate isDeeplyConstBelow ( ) { this .getBaseType ( ) .isDeeplyConstBelow ( ) }
1243+
1244+ override Specifier internal_getAnAdditionalSpecifier ( ) {
1245+ result = this .getBaseType ( ) .getASpecifier ( )
1246+ }
1247+ }
1248+
1249+ /**
1250+ * An instance of the C23 `typeof` or `typeof_unqual` operator taking an expression
1251+ * as its argument. For example:
1252+ * ```
1253+ * int a;
1254+ * typeof(a) b;
1255+ * ```
1256+ */
1257+ class TypeofExprType extends TypeofType {
1258+ TypeofExprType ( ) { decltypes ( underlyingElement ( this ) , _, 1 , _, _) }
1259+
1260+ override string getAPrimaryQlClass ( ) { result = "TypeofExprType" }
1261+
1262+ /**
1263+ * Gets the expression whose type is being obtained by this typeof.
1264+ */
1265+ Expr getExpr ( ) { decltypes ( underlyingElement ( this ) , unresolveElement ( result ) , _, _, _) }
1266+
1267+ override Location getLocation ( ) { result = this .getExpr ( ) .getLocation ( ) }
1268+ }
1269+
1270+ /**
1271+ * A type obtained by C23 `typeof` or `typeof_unqual` operator taking a type as its
1272+ * argument. For example:
1273+ * ```
1274+ * typeof_unqual(const int) b;
1275+ * ```
1276+ */
1277+ class TypeofTypeType extends TypeofType {
1278+ TypeofTypeType ( ) { type_operators ( underlyingElement ( this ) , _, 0 , _) }
1279+
1280+ /**
1281+ * Gets the expression whose type is being obtained by this typeof.
1282+ */
1283+ Type getType ( ) { type_operators ( underlyingElement ( this ) , unresolveElement ( result ) , _, _) }
1284+
1285+ override string getAPrimaryQlClass ( ) { result = "TypeofTypeType" }
1286+
1287+ override string toString ( ) { result = "typeof(...)" }
1288+ }
1289+
1290+ /**
1291+ * A type obtained by applying a type transforming intrinsic. For example:
1292+ * ```
1293+ * __make_unsigned(int) x;
1294+ * ```
1295+ */
1296+ class IntrinsicTransformedType extends Type {
1297+ int intrinsic ;
1298+
1299+ IntrinsicTransformedType ( ) {
1300+ type_operators ( underlyingElement ( this ) , _, intrinsic , _) and
1301+ intrinsic in [ 1 .. 19 ]
1302+ }
1303+
1304+ override string getAPrimaryQlClass ( ) { result = "IntrinsicTransformedType" }
1305+
1306+ override string toString ( ) { result = this .getIntrinsicName ( ) + "(...)" }
1307+
1308+ /**
1309+ * Gets the type immediately yielded by this transformation.
1310+ */
1311+ Type getBaseType ( ) { type_operators ( underlyingElement ( this ) , _, _, unresolveElement ( result ) ) }
1312+
1313+ /**
1314+ * Gets the type that is transformed.
1315+ */
1316+ Type getType ( ) { type_operators ( underlyingElement ( this ) , unresolveElement ( result ) , _, _) }
1317+
1318+ /**
1319+ * Gets the name of the intrinsic used to transform the type.
1320+ */
1321+ string getIntrinsicName ( ) {
1322+ intrinsic = 1 and result = "__underlying_type"
1323+ or
1324+ intrinsic = 2 and result = "__bases"
1325+ or
1326+ intrinsic = 3 and result = "__direct_bases"
1327+ or
1328+ intrinsic = 4 and result = "__add_lvalue_reference"
1329+ or
1330+ intrinsic = 5 and result = "__add_pointer"
1331+ or
1332+ intrinsic = 6 and result = "__add_rvalue_reference"
1333+ or
1334+ intrinsic = 7 and result = "__decay"
1335+ or
1336+ intrinsic = 8 and result = "__make_signed"
1337+ or
1338+ intrinsic = 9 and result = "__make_unsigned"
1339+ or
1340+ intrinsic = 10 and result = "__remove_all_extents"
1341+ or
1342+ intrinsic = 11 and result = "__remove_const"
1343+ or
1344+ intrinsic = 12 and result = "__remove_cv"
1345+ or
1346+ intrinsic = 13 and result = "__remove_cvref"
1347+ or
1348+ intrinsic = 14 and result = "__remove_extent"
1349+ or
1350+ intrinsic = 15 and result = "__remove_pointer"
1351+ or
1352+ intrinsic = 16 and result = "__remove_reference_t"
1353+ or
1354+ intrinsic = 17 and result = "__remove_restrict"
1355+ or
1356+ intrinsic = 18 and result = "__remove_volatile"
1357+ or
1358+ intrinsic = 19 and result = "__remove_reference"
1359+ }
1360+
1361+ override Type getUnderlyingType ( ) { result = this .getBaseType ( ) .getUnderlyingType ( ) }
1362+
1363+ override Type stripTopLevelSpecifiers ( ) { result = this .getBaseType ( ) .stripTopLevelSpecifiers ( ) }
1364+
1365+ override Type stripType ( ) { result = this .getBaseType ( ) .stripType ( ) }
1366+
1367+ override Type resolveTypedefs ( ) { result = this .getBaseType ( ) .resolveTypedefs ( ) }
1368+
1369+ override string getName ( ) { none ( ) }
1370+
1371+ override int getSize ( ) { result = this .getBaseType ( ) .getSize ( ) }
1372+
1373+ override int getAlignment ( ) { result = this .getBaseType ( ) .getAlignment ( ) }
1374+
1375+ override int getPointerIndirectionLevel ( ) {
1376+ result = this .getBaseType ( ) .getPointerIndirectionLevel ( )
1377+ }
1378+
1379+ override string explain ( ) {
1380+ result =
1381+ "application of " + this .getIntrinsicName ( ) + " resulting in {" + this .getBaseType ( ) .explain ( )
1382+ + "}"
1383+ }
1384+
1385+ override predicate involvesReference ( ) { this .getBaseType ( ) .involvesReference ( ) }
1386+
1387+ override predicate involvesTemplateParameter ( ) { this .getBaseType ( ) .involvesTemplateParameter ( ) }
1388+
1389+ override predicate isDeeplyConst ( ) { this .getBaseType ( ) .isDeeplyConst ( ) }
1390+
1391+ override predicate isDeeplyConstBelow ( ) { this .getBaseType ( ) .isDeeplyConstBelow ( ) }
1392+
1393+ override Specifier internal_getAnAdditionalSpecifier ( ) {
1394+ result = this .getBaseType ( ) .getASpecifier ( )
1395+ }
1396+ }
1397+
11861398/**
11871399 * A C/C++ pointer type. See 4.9.1.
11881400 * ```
0 commit comments