Skip to content

Commit fe73601

Browse files
authored
Merge pull request #9805 from github/redsun82/swift-type-repr-collapse
Swift: collapse `TypeRepr` hierarchy
2 parents 681e58c + 77401de commit fe73601

File tree

98 files changed

+657
-760
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

98 files changed

+657
-760
lines changed

swift/codegen/schema.yml

Lines changed: 3 additions & 88 deletions
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,7 @@ _includes:
77
_directories:
88
decl: Decl$|Context$
99
pattern: Pattern$
10-
type: Type$
11-
typerepr: TypeRepr$
10+
type: Type(Repr)?$
1211
expr: Expr$
1312
stmt: Stmt$
1413

@@ -185,6 +184,7 @@ Stmt:
185184

186185
TypeRepr:
187186
_extends: AstNode
187+
type: Type? # type can be absent on unresolved entities
188188

189189
FunctionType:
190190
_extends: AnyFunctionType
@@ -406,7 +406,6 @@ EnumIsCaseExpr:
406406
_extends: Expr
407407
_children:
408408
sub_expr: Expr
409-
type_repr: TypeRepr
410409
element: EnumElementDecl
411410

412411
ErrorExpr:
@@ -457,7 +456,7 @@ KeyPathDotExpr:
457456
KeyPathExpr:
458457
_extends: Expr
459458
_children:
460-
parsed_root: Expr?
459+
root: TypeRepr?
461460
parsed_path: Expr?
462461

463462
LazyInitializerExpr:
@@ -1177,87 +1176,3 @@ FloatLiteralExpr:
11771176
IntegerLiteralExpr:
11781177
_extends: NumberLiteralExpr
11791178
string_value: string
1180-
1181-
ErrorTypeRepr:
1182-
_extends: TypeRepr
1183-
1184-
AttributedTypeRepr:
1185-
_extends: TypeRepr
1186-
1187-
IdentTypeRepr:
1188-
_extends: TypeRepr
1189-
1190-
ComponentIdentTypeRepr:
1191-
_extends: IdentTypeRepr
1192-
1193-
SimpleIdentTypeRepr:
1194-
_extends: ComponentIdentTypeRepr
1195-
1196-
GenericIdentTypeRepr:
1197-
_extends: ComponentIdentTypeRepr
1198-
1199-
CompoundIdentTypeRepr:
1200-
_extends: IdentTypeRepr
1201-
1202-
FunctionTypeRepr:
1203-
_extends: TypeRepr
1204-
1205-
ArrayTypeRepr:
1206-
_extends: TypeRepr
1207-
1208-
DictionaryTypeRepr:
1209-
_extends: TypeRepr
1210-
1211-
OptionalTypeRepr:
1212-
_extends: TypeRepr
1213-
1214-
ImplicitlyUnwrappedOptionalTypeRepr:
1215-
_extends: TypeRepr
1216-
1217-
TupleTypeRepr:
1218-
_extends: TypeRepr
1219-
1220-
CompositionTypeRepr:
1221-
_extends: TypeRepr
1222-
1223-
MetatypeTypeRepr:
1224-
_extends: TypeRepr
1225-
1226-
ProtocolTypeRepr:
1227-
_extends: TypeRepr
1228-
1229-
OpaqueReturnTypeRepr:
1230-
_extends: TypeRepr
1231-
1232-
NamedOpaqueReturnTypeRepr:
1233-
_extends: TypeRepr
1234-
1235-
ExistentialTypeRepr:
1236-
_extends: TypeRepr
1237-
1238-
PlaceholderTypeRepr:
1239-
_extends: TypeRepr
1240-
1241-
SpecifierTypeRepr:
1242-
_extends: TypeRepr
1243-
1244-
InOutTypeRepr:
1245-
_extends: SpecifierTypeRepr
1246-
1247-
SharedTypeRepr:
1248-
_extends: SpecifierTypeRepr
1249-
1250-
OwnedTypeRepr:
1251-
_extends: SpecifierTypeRepr
1252-
1253-
IsolatedTypeRepr:
1254-
_extends: SpecifierTypeRepr
1255-
1256-
CompileTimeConstTypeRepr:
1257-
_extends: SpecifierTypeRepr
1258-
1259-
FixedTypeRepr:
1260-
_extends: TypeRepr
1261-
1262-
SilBoxTypeRepr:
1263-
_extends: TypeRepr

swift/extractor/infra/SwiftDispatcher.h

Lines changed: 16 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -61,8 +61,8 @@ class SwiftDispatcher {
6161
// This method gives a TRAP label for already emitted AST node.
6262
// If the AST node was not emitted yet, then the emission is dispatched to a corresponding
6363
// visitor (see `visit(T *)` methods below).
64-
template <typename E>
65-
TrapLabelOf<E> fetchLabel(E* e) {
64+
template <typename E, typename... Args>
65+
TrapLabelOf<E> fetchLabel(E* e, Args&&... args) {
6666
assert(e && "trying to fetch a label on nullptr, maybe fetchOptionalLabel is to be used?");
6767
// this is required so we avoid any recursive loop: a `fetchLabel` during the visit of `e` might
6868
// end up calling `fetchLabel` on `e` itself, so we want the visit of `e` to call `fetchLabel`
@@ -73,7 +73,7 @@ class SwiftDispatcher {
7373
return *l;
7474
}
7575
waitingForNewLabel = e;
76-
visit(e);
76+
visit(e, std::forward<Args>(args)...);
7777
// TODO when everything is moved to structured C++ classes, this should be moved to createEntry
7878
if (auto l = store.get(e)) {
7979
if constexpr (!std::is_base_of_v<swift::TypeBase, E>) {
@@ -168,10 +168,10 @@ class SwiftDispatcher {
168168
// return `std::optional(fetchLabel(arg))` if arg converts to true, otherwise std::nullopt
169169
// universal reference `Arg&&` is used to catch both temporary and non-const references, not
170170
// for perfect forwarding
171-
template <typename Arg>
172-
auto fetchOptionalLabel(Arg&& arg) -> std::optional<decltype(fetchLabel(arg))> {
171+
template <typename Arg, typename... Args>
172+
auto fetchOptionalLabel(Arg&& arg, Args&&... args) -> std::optional<decltype(fetchLabel(arg))> {
173173
if (arg) {
174-
return fetchLabel(arg);
174+
return fetchLabel(arg, std::forward<Args>(args)...);
175175
}
176176
return std::nullopt;
177177
}
@@ -263,9 +263,15 @@ class SwiftDispatcher {
263263

264264
template <typename Tag, typename T, typename... Ts>
265265
bool fetchLabelFromUnionCase(const llvm::PointerUnion<Ts...> u, TrapLabel<Tag>& output) {
266-
if (auto e = u.template dyn_cast<T>()) {
267-
output = fetchLabel(e);
268-
return true;
266+
// we rely on the fact that when we extract `ASTNode` instances (which only happens
267+
// on `BraceStmt` elements), we cannot encounter a standalone `TypeRepr` there, so we skip
268+
// this case; extracting `TypeRepr`s here would be problematic as we would not be able to
269+
// provide the corresponding type
270+
if constexpr (!std::is_same_v<T, swift::TypeRepr*>) {
271+
if (auto e = u.template dyn_cast<T>()) {
272+
output = fetchLabel(e);
273+
return true;
274+
}
269275
}
270276
return false;
271277
}
@@ -294,7 +300,7 @@ class SwiftDispatcher {
294300
virtual void visit(swift::CaseLabelItem* item) = 0;
295301
virtual void visit(swift::Expr* expr) = 0;
296302
virtual void visit(swift::Pattern* pattern) = 0;
297-
virtual void visit(swift::TypeRepr* type) = 0;
303+
virtual void visit(swift::TypeRepr* typeRepr, swift::Type type) = 0;
298304
virtual void visit(swift::TypeBase* type) = 0;
299305

300306
const swift::SourceManager& sourceManager;

swift/extractor/infra/SwiftTagTraits.h

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,6 @@ using SILBlockStorageTypeTag = SilBlockStorageTypeTag;
1414
using SILBoxTypeTag = SilBoxTypeTag;
1515
using SILFunctionTypeTag = SilFunctionTypeTag;
1616
using SILTokenTypeTag = SilTokenTypeTag;
17-
using SILBoxTypeReprTag = SilBoxTypeReprTag;
1817

1918
#define MAP_TYPE_TO_TAG(TYPE, TAG) \
2019
template <> \
@@ -60,9 +59,6 @@ MAP_TAG(Pattern);
6059
#include <swift/AST/PatternNodes.def>
6160

6261
MAP_TAG(TypeRepr);
63-
#define ABSTRACT_TYPEREPR(CLASS, PARENT) MAP_SUBTAG(CLASS##TypeRepr, PARENT)
64-
#define TYPEREPR(CLASS, PARENT) ABSTRACT_TYPEREPR(CLASS, PARENT)
65-
#include <swift/AST/TypeReprNodes.def>
6662

6763
MAP_TYPE_TO_TAG(TypeBase, TypeTag);
6864
#define ABSTRACT_TYPE(CLASS, PARENT) MAP_SUBTAG(CLASS##Type, PARENT)

swift/extractor/trap/BUILD.bazel

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
load("//swift:rules.bzl", "swift_cc_library")
22

3-
_dirs = ("", "decl/", "expr/", "pattern/", "stmt/", "type/", "typerepr/")
3+
_dirs = ("", "decl/", "expr/", "pattern/", "stmt/", "type/")
44

55
genrule(
66
name = "cppgen",

swift/extractor/visitors/ExprVisitor.cpp

Lines changed: 12 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -188,9 +188,8 @@ void ExprVisitor::visitEnumIsCaseExpr(swift::EnumIsCaseExpr* expr) {
188188
assert(expr->getCaseTypeRepr() && "EnumIsCaseExpr has CaseTypeRepr");
189189
assert(expr->getEnumElement() && "EnumIsCaseExpr has EnumElement");
190190
auto subExpr = dispatcher_.fetchLabel(expr->getSubExpr());
191-
auto typeRepr = dispatcher_.fetchLabel(expr->getCaseTypeRepr());
192191
auto enumElement = dispatcher_.fetchLabel(expr->getEnumElement());
193-
dispatcher_.emit(EnumIsCaseExprsTrap{label, subExpr, typeRepr, enumElement});
192+
dispatcher_.emit(EnumIsCaseExprsTrap{label, subExpr, enumElement});
194193
}
195194

196195
void ExprVisitor::visitMakeTemporarilyEscapableExpr(swift::MakeTemporarilyEscapableExpr* expr) {
@@ -288,7 +287,9 @@ void ExprVisitor::visitErasureExpr(swift::ErasureExpr* expr) {
288287

289288
codeql::TypeExpr ExprVisitor::translateTypeExpr(const swift::TypeExpr& expr) {
290289
TypeExpr entry{dispatcher_.assignNewLabel(expr)};
291-
entry.type_repr = dispatcher_.fetchOptionalLabel(expr.getTypeRepr());
290+
if (expr.getTypeRepr() && expr.getInstanceType()) {
291+
entry.type_repr = dispatcher_.fetchLabel(expr.getTypeRepr(), expr.getInstanceType());
292+
}
292293
return entry;
293294
}
294295

@@ -478,9 +479,14 @@ void ExprVisitor::visitKeyPathExpr(swift::KeyPathExpr* expr) {
478479
auto pathLabel = dispatcher_.fetchLabel(path);
479480
dispatcher_.emit(KeyPathExprParsedPathsTrap{label, pathLabel});
480481
}
481-
if (auto root = expr->getParsedRoot()) {
482-
auto rootLabel = dispatcher_.fetchLabel(root);
483-
dispatcher_.emit(KeyPathExprParsedRootsTrap{label, rootLabel});
482+
// TODO maybe move this logic to QL?
483+
if (auto rootTypeRepr = expr->getRootType()) {
484+
auto keyPathType = expr->getType()->getAs<swift::BoundGenericClassType>();
485+
assert(keyPathType && "KeyPathExpr must have BoundGenericClassType");
486+
auto keyPathTypeArgs = keyPathType->getGenericArgs();
487+
assert(keyPathTypeArgs.size() != 0 && "KeyPathExpr type must have generic args");
488+
auto rootLabel = dispatcher_.fetchLabel(rootTypeRepr, keyPathTypeArgs[0]);
489+
dispatcher_.emit(KeyPathExprRootsTrap{label, rootLabel});
484490
}
485491
}
486492
}

swift/extractor/visitors/PatternVisitor.cpp

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,8 @@ void PatternVisitor::visitTypedPattern(swift::TypedPattern* pattern) {
1818
assert(pattern->getSubPattern() && "expect TypedPattern to have a SubPattern");
1919
dispatcher_.emit(TypedPatternsTrap{label, dispatcher_.fetchLabel(pattern->getSubPattern())});
2020
if (auto typeRepr = pattern->getTypeRepr()) {
21-
dispatcher_.emit(
22-
TypedPatternTypeReprsTrap{label, dispatcher_.fetchLabel(pattern->getTypeRepr())});
21+
dispatcher_.emit(TypedPatternTypeReprsTrap{
22+
label, dispatcher_.fetchLabel(pattern->getTypeRepr(), pattern->getType())});
2323
}
2424
}
2525

@@ -63,7 +63,8 @@ void PatternVisitor::visitIsPattern(swift::IsPattern* pattern) {
6363
dispatcher_.emit(IsPatternsTrap{label});
6464

6565
if (auto typeRepr = pattern->getCastTypeRepr()) {
66-
dispatcher_.emit(IsPatternCastTypeReprsTrap{label, dispatcher_.fetchLabel(typeRepr)});
66+
dispatcher_.emit(IsPatternCastTypeReprsTrap{
67+
label, dispatcher_.fetchLabel(typeRepr, pattern->getCastType())});
6768
}
6869
if (auto subPattern = pattern->getSubPattern()) {
6970
dispatcher_.emit(IsPatternSubPatternsTrap{label, dispatcher_.fetchLabel(subPattern)});

swift/extractor/visitors/SwiftVisitor.h

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@
55
#include "swift/extractor/visitors/ExprVisitor.h"
66
#include "swift/extractor/visitors/StmtVisitor.h"
77
#include "swift/extractor/visitors/TypeVisitor.h"
8-
#include "swift/extractor/visitors/TypeReprVisitor.h"
98
#include "swift/extractor/visitors/PatternVisitor.h"
109

1110
namespace codeql {
@@ -32,13 +31,14 @@ class SwiftVisitor : private SwiftDispatcher {
3231
void visit(swift::CaseLabelItem* item) override { stmtVisitor.visitCaseLabelItem(item); }
3332
void visit(swift::Expr* expr) override { exprVisitor.visit(expr); }
3433
void visit(swift::Pattern* pattern) override { patternVisitor.visit(pattern); }
35-
void visit(swift::TypeRepr* type) override { typeReprVisitor.visit(type); }
3634
void visit(swift::TypeBase* type) override { typeVisitor.visit(type); }
35+
void visit(swift::TypeRepr* typeRepr, swift::Type type) override {
36+
emit(typeVisitor.translateTypeRepr(*typeRepr, type));
37+
}
3738

3839
DeclVisitor declVisitor{*this};
3940
ExprVisitor exprVisitor{*this};
4041
StmtVisitor stmtVisitor{*this};
41-
TypeReprVisitor typeReprVisitor{*this};
4242
TypeVisitor typeVisitor{*this};
4343
PatternVisitor patternVisitor{*this};
4444
};

swift/extractor/visitors/TypeReprVisitor.cpp

Lines changed: 0 additions & 3 deletions
This file was deleted.

swift/extractor/visitors/TypeReprVisitor.h

Lines changed: 0 additions & 13 deletions
This file was deleted.

swift/extractor/visitors/TypeVisitor.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,12 @@ void TypeVisitor::visit(swift::TypeBase* type) {
99
dispatcher_.emit(TypesTrap{label, type->getString(), canonicalLabel});
1010
}
1111

12+
codeql::TypeRepr TypeVisitor::translateTypeRepr(const swift::TypeRepr& typeRepr, swift::Type type) {
13+
auto entry = dispatcher_.createEntry(typeRepr);
14+
entry.type = dispatcher_.fetchOptionalLabel(type);
15+
return entry;
16+
}
17+
1218
void TypeVisitor::visitProtocolType(swift::ProtocolType* type) {
1319
auto label = dispatcher_.assignNewLabel(type);
1420
dispatcher_.emit(ProtocolTypesTrap{label});

0 commit comments

Comments
 (0)