Skip to content

Commit f49d92a

Browse files
johnniwintherCommit Queue
authored andcommitted
[cfe] Use LookupResult for constructor lookup
This adds `LookupResult.isInvalidLookup` to the handle invalid lookup results and uses this to avoid a lot of cascading error messages. This is a step towards removing ProblemBuilder, AmbiguousBuilder and reliance on `NamedBuilder.isDuplicate` in lookups. Change-Id: Ia9d558ce55b45567607282295dd1e54e6187f9c5 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/441880 Reviewed-by: Chloe Stefantsova <[email protected]> Commit-Queue: Johnni Winther <[email protected]> Reviewed-by: Erik Ernst <[email protected]>
1 parent 967b359 commit f49d92a

File tree

223 files changed

+3175
-9241
lines changed

Some content is hidden

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

223 files changed

+3175
-9241
lines changed

pkg/_fe_analyzer_shared/lib/src/messages/codes_generated.dart

Lines changed: 0 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -18043,42 +18043,6 @@ const MessageCode messageUnnamedObjectPatternField = const MessageCode(
1804318043
r"""Try adding a pattern name or ':' before the pattern.""",
1804418044
);
1804518045

18046-
// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
18047-
const Template<Message Function(String name, String name2)>
18048-
templateUnresolvedPrefixInTypeAnnotation =
18049-
const Template<Message Function(String name, String name2)>(
18050-
"UnresolvedPrefixInTypeAnnotation",
18051-
problemMessageTemplate:
18052-
r"""'#name.#name2' can't be used as a type because '#name' isn't defined.""",
18053-
withArguments: _withArgumentsUnresolvedPrefixInTypeAnnotation,
18054-
);
18055-
18056-
// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
18057-
const Code<Message Function(String name, String name2)>
18058-
codeUnresolvedPrefixInTypeAnnotation =
18059-
const Code<Message Function(String name, String name2)>(
18060-
"UnresolvedPrefixInTypeAnnotation",
18061-
analyzerCodes: <String>["NOT_A_TYPE"],
18062-
);
18063-
18064-
// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
18065-
Message _withArgumentsUnresolvedPrefixInTypeAnnotation(
18066-
String name, String name2) {
18067-
if (name.isEmpty) throw 'No name provided';
18068-
name = demangleMixinApplicationName(name);
18069-
if (name2.isEmpty) throw 'No name provided';
18070-
name2 = demangleMixinApplicationName(name2);
18071-
return new Message(
18072-
codeUnresolvedPrefixInTypeAnnotation,
18073-
problemMessage:
18074-
"""'${name}.${name2}' can't be used as a type because '${name}' isn't defined.""",
18075-
arguments: {
18076-
'name': name,
18077-
'name2': name2,
18078-
},
18079-
);
18080-
}
18081-
1808218046
// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
1808318047
const Code<Null> codeUnsoundSwitchExpressionError =
1808418048
messageUnsoundSwitchExpressionError;

pkg/front_end/lib/src/base/identifiers.dart

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,7 @@ class SimpleIdentifier extends IdentifierImpl {
7878
return new QualifiedNameGenerator(qualifier, token);
7979
}
8080

81+
// Coverage-ignore(suite): Not run.
8182
QualifiedNameBuilder withBuilderQualifier(Builder qualifier) {
8283
return new QualifiedNameBuilder(qualifier, token);
8384
}
@@ -187,6 +188,7 @@ class QualifiedNameGenerator extends QualifiedName {
187188
String toString() => "qualified-name-generator($qualifier, $name)";
188189
}
189190

191+
// Coverage-ignore(suite): Not run.
190192
class QualifiedNameBuilder extends QualifiedName {
191193
final Builder qualifier;
192194

@@ -195,7 +197,6 @@ class QualifiedNameBuilder extends QualifiedName {
195197
Token get suffix => token;
196198

197199
@override
198-
// Coverage-ignore(suite): Not run.
199200
int get firstOffset => qualifier.fileOffset;
200201

201202
@override

pkg/front_end/lib/src/base/incremental_compiler.dart

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1712,17 +1712,15 @@ class IncrementalCompiler implements IncrementalKernelGenerator {
17121712
extensionName = beforeDot;
17131713
if (builder is ExtensionBuilder) {
17141714
extension = builder.extension;
1715-
Builder? subBuilder =
1716-
builder.lookupLocalMember(afterDot, setter: false);
1715+
Builder? subBuilder = builder.lookupLocalMember(afterDot)?.getable;
17171716
if (subBuilder is MemberBuilder) {
17181717
if (subBuilder.isExtensionInstanceMember) {
17191718
isStatic = false;
17201719
}
17211720
}
17221721
} else if (builder is ExtensionTypeDeclarationBuilder) {
17231722
extensionType = builder.extensionTypeDeclaration;
1724-
Builder? subBuilder =
1725-
builder.lookupLocalMember(afterDot, setter: false);
1723+
Builder? subBuilder = builder.lookupLocalMember(afterDot)?.getable;
17261724
if (subBuilder is MemberBuilder) {
17271725
if (subBuilder.isExtensionTypeInstanceMember) {
17281726
List<VariableDeclaration>? positionals =

pkg/front_end/lib/src/base/lookup_result.dart

Lines changed: 149 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,13 @@
22
// for details. All rights reserved. Use of this source code is governed by a
33
// BSD-style license that can be found in the LICENSE file.
44

5+
import 'package:kernel/ast.dart';
6+
57
import '../builder/builder.dart';
8+
import '../builder/declaration_builders.dart';
9+
import '../builder/member_builder.dart';
10+
import '../codes/cfe_codes.dart';
11+
import 'compiler_context.dart';
612
import 'scope.dart';
713

814
abstract class LookupResult {
@@ -12,6 +18,50 @@ abstract class LookupResult {
1218
/// The [NamedBuilder] used for writing to this entity, if any.
1319
NamedBuilder? get setable;
1420

21+
/// Returns `true` if the result is invalid.
22+
///
23+
/// For instance because of duplicate declaration or because of an invalid
24+
/// scope origin.
25+
bool get isInvalidLookup;
26+
27+
static LocatedMessage createDuplicateMessage(LookupResult lookupResult,
28+
{DeclarationBuilder? enclosingDeclaration,
29+
required String name,
30+
required Uri fileUri,
31+
required int fileOffset,
32+
required int length}) {
33+
if (name.isEmpty) {
34+
if (enclosingDeclaration != null) {
35+
name = enclosingDeclaration.name;
36+
} else {
37+
name = 'new';
38+
}
39+
length = noLength;
40+
}
41+
Message message = templateDuplicatedDeclarationUse.withArguments(name);
42+
return message.withLocation(fileUri, fileOffset, length);
43+
}
44+
45+
static InvalidExpression createDuplicateExpression(LookupResult lookupResult,
46+
{required CompilerContext context,
47+
DeclarationBuilder? enclosingDeclaration,
48+
required String name,
49+
required Uri fileUri,
50+
required int fileOffset,
51+
required int length}) {
52+
String text = context
53+
.format(
54+
createDuplicateMessage(lookupResult,
55+
enclosingDeclaration: enclosingDeclaration,
56+
name: name,
57+
fileUri: fileUri,
58+
fileOffset: fileOffset,
59+
length: length),
60+
Severity.error)
61+
.plain;
62+
return new InvalidExpression(text)..fileOffset = fileOffset;
63+
}
64+
1565
/// Creates a [LookupResult] for [getable] and [setable] which filters
1666
/// instance members if [staticOnly] is `true`, and creates an
1767
/// [AmbiguousBuilder] for duplicates using [fileUri] and [fileOffset].
@@ -26,6 +76,7 @@ abstract class LookupResult {
2676
bool changed = false;
2777
if (getable != null) {
2878
if (getable.next != null) {
79+
// Coverage-ignore-block(suite): Not run.
2980
getable = new AmbiguousBuilder(name, getable, fileOffset, fileUri);
3081
changed = true;
3182
}
@@ -36,6 +87,7 @@ abstract class LookupResult {
3687
}
3788
if (setable != null) {
3889
if (setable.next != null) {
90+
// Coverage-ignore-block(suite): Not run.
3991
setable = new AmbiguousBuilder(name, setable, fileOffset, fileUri);
4092
changed = true;
4193
}
@@ -91,6 +143,7 @@ abstract class LookupResult {
91143
return new GetableSetableResult(getable, setable!);
92144
}
93145
} else {
146+
// Coverage-ignore-block(suite): Not run.
94147
if (getable != null && setable != null) {
95148
return new GetableSetableResult(getable, setable);
96149
} else if (getable != null) {
@@ -110,12 +163,12 @@ abstract class LookupResult {
110163
if (existing != null) {
111164
if (setter) {
112165
assert(existing.getable != null,
113-
"No existing getable for $name: $existing.");
166+
"No existing getable for $name: $existing, trying to add $member.");
114167
content[name] = new GetableSetableResult(existing.getable!, member);
115168
return;
116169
} else {
117170
assert(existing.setable != null,
118-
"No existing setable for $name: $existing.");
171+
"No existing setable for $name: $existing, trying to add $member.");
119172
content[name] = new GetableSetableResult(member, existing.setable!);
120173
return;
121174
}
@@ -130,7 +183,68 @@ abstract class LookupResult {
130183
}
131184
}
132185

133-
class GetableResult implements LookupResult {
186+
abstract class InvalidLookupResult implements LookupResult {
187+
factory InvalidLookupResult(LocatedMessage message) =
188+
_InvalidLookupResultImpl;
189+
190+
LocatedMessage get message;
191+
}
192+
193+
// Coverage-ignore(suite): Not run.
194+
class _InvalidLookupResultImpl implements InvalidLookupResult {
195+
@override
196+
final LocatedMessage message;
197+
198+
_InvalidLookupResultImpl(this.message);
199+
200+
@override
201+
bool get isInvalidLookup => true;
202+
203+
@override
204+
NamedBuilder? get getable => null;
205+
206+
@override
207+
NamedBuilder? get setable => null;
208+
}
209+
210+
abstract class MemberLookupResult implements LookupResult {
211+
/// The [MemberBuilder] used for reading this entity, if any.
212+
@override
213+
MemberBuilder? get getable;
214+
215+
/// The [MemberBuilder] used for writing to this entity, if any.
216+
@override
217+
MemberBuilder? get setable;
218+
219+
/// Return `true` if this [MemberBuilder]s of this lookup result are accessed
220+
/// statically.
221+
bool get isStatic;
222+
}
223+
224+
class InvalidMemberLookupResult
225+
implements InvalidLookupResult, MemberLookupResult {
226+
@override
227+
final LocatedMessage message;
228+
229+
InvalidMemberLookupResult(this.message);
230+
231+
@override
232+
bool get isInvalidLookup => true;
233+
234+
@override
235+
// Coverage-ignore(suite): Not run.
236+
MemberBuilder? get getable => null;
237+
238+
@override
239+
// Coverage-ignore(suite): Not run.
240+
MemberBuilder? get setable => null;
241+
242+
@override
243+
// Coverage-ignore(suite): Not run.
244+
bool get isStatic => true;
245+
}
246+
247+
class GetableResult with LookupResultMixin implements LookupResult {
134248
@override
135249
final NamedBuilder getable;
136250

@@ -140,7 +254,8 @@ class GetableResult implements LookupResult {
140254
NamedBuilder? get setable => null;
141255
}
142256

143-
class SetableResult implements LookupResult {
257+
// Coverage-ignore(suite): Not run.
258+
class SetableResult with LookupResultMixin implements LookupResult {
144259
@override
145260
final NamedBuilder setable;
146261

@@ -150,7 +265,7 @@ class SetableResult implements LookupResult {
150265
NamedBuilder? get getable => null;
151266
}
152267

153-
class GetableSetableResult implements LookupResult {
268+
class GetableSetableResult with LookupResultMixin implements LookupResult {
154269
@override
155270
final NamedBuilder getable;
156271

@@ -159,3 +274,32 @@ class GetableSetableResult implements LookupResult {
159274

160275
GetableSetableResult(this.getable, this.setable);
161276
}
277+
278+
mixin LookupResultMixin implements LookupResult {
279+
@override
280+
bool get isInvalidLookup =>
281+
(getable?.isDuplicate ?? false) || (setable?.isDuplicate ?? false);
282+
}
283+
284+
class DuplicateMemberLookupResult implements MemberLookupResult {
285+
final List<MemberBuilder> declarations;
286+
287+
DuplicateMemberLookupResult(this.declarations);
288+
289+
@override
290+
MemberBuilder? get getable => null;
291+
292+
@override
293+
bool get isInvalidLookup => true;
294+
295+
@override
296+
MemberBuilder? get setable => null;
297+
298+
/// Return `true` if this [MemberBuilder]s of this lookup result are accessed
299+
/// statically.
300+
///
301+
/// Since this lookup can contain both static and non-static members, we
302+
/// return `true` so that it will not be filtered in static member lookup.
303+
@override
304+
bool get isStatic => true;
305+
}

0 commit comments

Comments
 (0)