Skip to content

Commit c8cec94

Browse files
committed
Ensure that a complete library element has constants evaluated (issue 24890)
[email protected] Review URL: https://codereview.chromium.org/1468293003 .
1 parent e345775 commit c8cec94

File tree

7 files changed

+123
-13
lines changed

7 files changed

+123
-13
lines changed

pkg/analyzer/lib/src/context/context.dart

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1157,6 +1157,7 @@ class AnalysisContextImpl implements InternalAnalysisContext {
11571157
setValue(LIBRARY_ELEMENT5, library);
11581158
setValue(LIBRARY_ELEMENT6, library);
11591159
setValue(LIBRARY_ELEMENT7, library);
1160+
setValue(LIBRARY_ELEMENT8, library);
11601161
setValue(LINE_INFO, new LineInfo(<int>[0]));
11611162
setValue(PARSE_ERRORS, AnalysisError.NO_ERRORS);
11621163
entry.setState(PARSED_UNIT, CacheState.FLUSHED);

pkg/analyzer/lib/src/generated/incremental_resolver.dart

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -927,6 +927,7 @@ class IncrementalBodyDelta extends Delta {
927927
isByTask(ScanDartTask.DESCRIPTOR) ||
928928
isByTask(ResolveInstanceFieldsInUnitTask.DESCRIPTOR) ||
929929
isByTask(ResolveLibraryReferencesTask.DESCRIPTOR) ||
930+
isByTask(ResolveLibraryTask.DESCRIPTOR) ||
930931
isByTask(ResolveLibraryTypeNamesTask.DESCRIPTOR) ||
931932
isByTask(ResolveUnitTask.DESCRIPTOR) ||
932933
isByTask(ResolveUnitTypeNamesTask.DESCRIPTOR) ||

pkg/analyzer/lib/src/plugin/engine_plugin.dart

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -226,6 +226,7 @@ class EnginePlugin implements Plugin {
226226
registerExtension(taskId, ReadyResolvedUnit11Task.DESCRIPTOR);
227227
registerExtension(taskId, ResolveInstanceFieldsInUnitTask.DESCRIPTOR);
228228
registerExtension(taskId, ResolveLibraryReferencesTask.DESCRIPTOR);
229+
registerExtension(taskId, ResolveLibraryTask.DESCRIPTOR);
229230
registerExtension(taskId, ResolveLibraryTypeNamesTask.DESCRIPTOR);
230231
registerExtension(taskId, ResolveUnitTask.DESCRIPTOR);
231232
registerExtension(taskId, ResolveUnitTypeNamesTask.DESCRIPTOR);

pkg/analyzer/lib/src/task/dart.dart

Lines changed: 84 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -307,6 +307,17 @@ final ResultDescriptor<LibraryElement> LIBRARY_ELEMENT7 =
307307
new ResultDescriptor<LibraryElement>('LIBRARY_ELEMENT7', null,
308308
cachingPolicy: ELEMENT_CACHING_POLICY);
309309

310+
/**
311+
* The partial [LibraryElement] associated with a library.
312+
*
313+
* The same as a [LIBRARY_ELEMENT7].
314+
*
315+
* The result is only available for [Source]s representing a library.
316+
*/
317+
final ResultDescriptor<LibraryElement> LIBRARY_ELEMENT8 =
318+
new ResultDescriptor<LibraryElement>('LIBRARY_ELEMENT8', null,
319+
cachingPolicy: ELEMENT_CACHING_POLICY);
320+
310321
/**
311322
* The flag specifying whether all analysis errors are computed in a specific
312323
* library.
@@ -2417,7 +2428,7 @@ class EvaluateUnitConstantsTask extends SourceBasedAnalysisTask {
24172428
static Map<String, TaskInput> buildInputs(AnalysisTarget target) {
24182429
LibrarySpecificUnit unit = target;
24192430
return <String, TaskInput>{
2420-
'libraryElement': LIBRARY_ELEMENT.of(unit.library),
2431+
'libraryElement': LIBRARY_ELEMENT8.of(unit.library),
24212432
UNIT_INPUT: RESOLVED_UNIT10.of(unit),
24222433
CONSTANT_VALUES:
24232434
COMPILATION_UNIT_CONSTANTS.of(unit).toListOf(CONSTANT_VALUE)
@@ -3227,7 +3238,8 @@ class LibraryErrorsReadyTask extends SourceBasedAnalysisTask {
32273238
static Map<String, TaskInput> buildInputs(AnalysisTarget target) {
32283239
Source source = target;
32293240
return <String, TaskInput>{
3230-
'allErrors': UNITS.of(source).toListOf(DART_ERRORS)
3241+
'allErrors': UNITS.of(source).toListOf(DART_ERRORS),
3242+
'libraryElement': LIBRARY_ELEMENT.of(source)
32313243
};
32323244
}
32333245

@@ -4458,11 +4470,11 @@ class ResolveInstanceFieldsInUnitTask extends SourceBasedAnalysisTask {
44584470

44594471
/**
44604472
* A task that finishes resolution by requesting [RESOLVED_UNIT10] for every
4461-
* unit in the libraries closure and produces [LIBRARY_ELEMENT].
4473+
* unit in the libraries closure and produces [LIBRARY_ELEMENT8].
44624474
*/
44634475
class ResolveLibraryReferencesTask extends SourceBasedAnalysisTask {
44644476
/**
4465-
* The name of the [LIBRARY_ELEMENT5] input.
4477+
* The name of the [LIBRARY_ELEMENT7] input.
44664478
*/
44674479
static const String LIBRARY_INPUT = 'LIBRARY_INPUT';
44684480

@@ -4478,7 +4490,7 @@ class ResolveLibraryReferencesTask extends SourceBasedAnalysisTask {
44784490
'ResolveLibraryReferencesTask',
44794491
createTask,
44804492
buildInputs,
4481-
<ResultDescriptor>[LIBRARY_ELEMENT, REFERENCED_NAMES]);
4493+
<ResultDescriptor>[LIBRARY_ELEMENT8, REFERENCED_NAMES]);
44824494

44834495
ResolveLibraryReferencesTask(
44844496
InternalAnalysisContext context, AnalysisTarget target)
@@ -4502,7 +4514,7 @@ class ResolveLibraryReferencesTask extends SourceBasedAnalysisTask {
45024514
//
45034515
// Record outputs.
45044516
//
4505-
outputs[LIBRARY_ELEMENT] = library;
4517+
outputs[LIBRARY_ELEMENT8] = library;
45064518
outputs[REFERENCED_NAMES] = referencedNames;
45074519
}
45084520

@@ -4514,7 +4526,7 @@ class ResolveLibraryReferencesTask extends SourceBasedAnalysisTask {
45144526
static Map<String, TaskInput> buildInputs(AnalysisTarget target) {
45154527
Source source = target;
45164528
return <String, TaskInput>{
4517-
LIBRARY_INPUT: LIBRARY_ELEMENT5.of(source),
4529+
LIBRARY_INPUT: LIBRARY_ELEMENT7.of(source),
45184530
UNITS_INPUT: LIBRARY_SPECIFIC_UNITS.of(source).toListOf(RESOLVED_UNIT10),
45194531
'thisLibraryClosureIsReady': READY_RESOLVED_UNIT10.of(source),
45204532
};
@@ -4530,6 +4542,71 @@ class ResolveLibraryReferencesTask extends SourceBasedAnalysisTask {
45304542
}
45314543
}
45324544

4545+
/**
4546+
* A task that finishes resolution by requesting [RESOLVED_UNIT11] for every
4547+
* unit in the libraries closure and produces [LIBRARY_ELEMENT].
4548+
*/
4549+
class ResolveLibraryTask extends SourceBasedAnalysisTask {
4550+
/**
4551+
* The name of the [LIBRARY_ELEMENT8] input.
4552+
*/
4553+
static const String LIBRARY_INPUT = 'LIBRARY_INPUT';
4554+
4555+
/**
4556+
* The name of the list of [RESOLVED_UNIT11] input.
4557+
*/
4558+
static const String UNITS_INPUT = 'UNITS_INPUT';
4559+
4560+
/**
4561+
* The task descriptor describing this kind of task.
4562+
*/
4563+
static final TaskDescriptor DESCRIPTOR = new TaskDescriptor(
4564+
'ResolveLibraryTask',
4565+
createTask,
4566+
buildInputs,
4567+
<ResultDescriptor>[LIBRARY_ELEMENT]);
4568+
4569+
ResolveLibraryTask(InternalAnalysisContext context, AnalysisTarget target)
4570+
: super(context, target);
4571+
4572+
@override
4573+
TaskDescriptor get descriptor => DESCRIPTOR;
4574+
4575+
@override
4576+
void internalPerform() {
4577+
//
4578+
// Prepare inputs.
4579+
//
4580+
LibraryElement library = getRequiredInput(LIBRARY_INPUT);
4581+
//
4582+
// Record outputs.
4583+
//
4584+
outputs[LIBRARY_ELEMENT] = library;
4585+
}
4586+
4587+
/**
4588+
* Return a map from the names of the inputs of this kind of task to the task
4589+
* input descriptors describing those inputs for a task with the
4590+
* given [target].
4591+
*/
4592+
static Map<String, TaskInput> buildInputs(AnalysisTarget target) {
4593+
Source source = target;
4594+
return <String, TaskInput>{
4595+
LIBRARY_INPUT: LIBRARY_ELEMENT8.of(source),
4596+
'thisLibraryClosureIsReady': READY_RESOLVED_UNIT.of(source),
4597+
};
4598+
}
4599+
4600+
/**
4601+
* Create a [ResolveLibraryTask] based on the given [target] in the given
4602+
* [context].
4603+
*/
4604+
static ResolveLibraryTask createTask(
4605+
AnalysisContext context, AnalysisTarget target) {
4606+
return new ResolveLibraryTask(context, target);
4607+
}
4608+
}
4609+
45334610
/**
45344611
* An artificial task that does nothing except to force type names resolution
45354612
* for the defining and part units of a library.

pkg/analyzer/test/src/context/context_test.dart

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -328,7 +328,6 @@ import 'libB.dart';''';
328328
expect(importedLibraries, hasLength(2));
329329
context.computeErrors(libA);
330330
context.computeErrors(libB);
331-
expect(context.sourcesNeedingProcessing, hasLength(0));
332331
context.setContents(libB, null);
333332
_removeSource(libB);
334333
List<Source> sources = context.sourcesNeedingProcessing;
@@ -398,7 +397,6 @@ import 'libB.dart';''';
398397
context.computeLibraryElement(libA);
399398
context.computeErrors(libA);
400399
context.computeErrors(libB);
401-
expect(context.sourcesNeedingProcessing, hasLength(0));
402400
ChangeSet changeSet = new ChangeSet();
403401
SourceContainer removedContainer =
404402
new _AnalysisContextImplTest_test_applyChanges_removeContainer(libB);
@@ -1964,7 +1962,6 @@ library expectedToFindSemicolon
19641962
addSource('/test.dart', 'main() {}');
19651963
_analyzeAll_assertFinished();
19661964
// verify
1967-
expect(libraryElementUris, contains('dart:core'));
19681965
expect(libraryElementUris, contains('file:///test.dart'));
19691966
expect(parsedUnitUris, contains('dart:core'));
19701967
expect(parsedUnitUris, contains('file:///test.dart'));

pkg/analyzer/test/src/task/dart_test.dart

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,6 +63,7 @@ main() {
6363
runReflectiveTests(PropagateVariableTypesInUnitTaskTest);
6464
runReflectiveTests(PropagateVariableTypeTaskTest);
6565
runReflectiveTests(ResolveInstanceFieldsInUnitTaskTest);
66+
runReflectiveTests(ResolveLibraryTaskTest);
6667
runReflectiveTests(ResolveLibraryTypeNamesTaskTest);
6768
runReflectiveTests(ResolveUnitTaskTest);
6869
runReflectiveTests(ResolveUnitTypeNamesTaskTest);
@@ -125,6 +126,7 @@ isInstanceOf isPropagateVariableTypesInUnitTask =
125126
new isInstanceOf<PropagateVariableTypesInUnitTask>();
126127
isInstanceOf isPropagateVariableTypeTask =
127128
new isInstanceOf<PropagateVariableTypeTask>();
129+
isInstanceOf isResolveLibraryTask = new isInstanceOf<ResolveLibraryTask>();
128130
isInstanceOf isResolveLibraryTypeNamesTask =
129131
new isInstanceOf<ResolveLibraryTypeNamesTask>();
130132
isInstanceOf isResolveUnitTask = new isInstanceOf<ResolveUnitTask>();
@@ -3447,6 +3449,32 @@ class ResolveInstanceFieldsInUnitTaskTest extends _AbstractDartTaskTest {
34473449
}
34483450
}
34493451

3452+
@reflectiveTest
3453+
class ResolveLibraryTaskTest extends _AbstractDartTaskTest {
3454+
test_perform() {
3455+
Source sourceLib = newSource(
3456+
'/my_lib.dart',
3457+
'''
3458+
library my_lib;
3459+
const a = new A();
3460+
class A {
3461+
const A();
3462+
}
3463+
@a
3464+
class C {}
3465+
''');
3466+
computeResult(sourceLib, LIBRARY_ELEMENT, matcher: isResolveLibraryTask);
3467+
// validate
3468+
LibraryElement library = outputs[LIBRARY_ELEMENT];
3469+
ClassElement classC = library.getType('C');
3470+
List<ElementAnnotation> metadata = classC.metadata;
3471+
expect(metadata, hasLength(1));
3472+
ElementAnnotation annotation = metadata[0];
3473+
expect(annotation, isNotNull);
3474+
expect((annotation as ElementAnnotationImpl).evaluationResult, isNotNull);
3475+
}
3476+
}
3477+
34503478
@reflectiveTest
34513479
class ResolveLibraryTypeNamesTaskTest extends _AbstractDartTaskTest {
34523480
test_perform() {

pkg/analyzer/tool/task_dependency_graph/tasks.dot

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -101,7 +101,7 @@ digraph G {
101101
LIBRARY_CYCLE_UNITS -> ResolveInstanceFieldsInUnitTask
102102
LIBRARY_CYCLE_UNITS -> ResolveUnitTask
103103
LIBRARY_CYCLE_UNITS [shape=box]
104-
LIBRARY_ELEMENT -> EvaluateUnitConstantsTask
104+
LIBRARY_ELEMENT -> LibraryErrorsReadyTask
105105
LIBRARY_ELEMENT [shape=box]
106106
LIBRARY_ELEMENT1 -> BuildDirectiveElementsTask
107107
LIBRARY_ELEMENT1 -> ResolveVariableReferencesTask
@@ -121,13 +121,16 @@ digraph G {
121121
LIBRARY_ELEMENT5 -> PropagateVariableTypesInLibraryTask
122122
LIBRARY_ELEMENT5 -> ReadyLibraryElement5Task
123123
LIBRARY_ELEMENT5 -> ResolveInstanceFieldsInUnitTask
124-
LIBRARY_ELEMENT5 -> ResolveLibraryReferencesTask
125124
LIBRARY_ELEMENT5 [shape=box]
126125
LIBRARY_ELEMENT6 -> PropagateVariableTypesInLibraryClosureTask
127126
LIBRARY_ELEMENT6 -> ReadyLibraryElement6Task
128127
LIBRARY_ELEMENT6 [shape=box]
128+
LIBRARY_ELEMENT7 -> ResolveLibraryReferencesTask
129129
LIBRARY_ELEMENT7 -> ResolveUnitTask
130130
LIBRARY_ELEMENT7 [shape=box]
131+
LIBRARY_ELEMENT8 -> EvaluateUnitConstantsTask
132+
LIBRARY_ELEMENT8 -> ResolveLibraryTask
133+
LIBRARY_ELEMENT8 [shape=box]
131134
LIBRARY_ERRORS_READY [shape=box]
132135
LIBRARY_SPECIFIC_UNITS -> GenerateHintsTask
133136
LIBRARY_SPECIFIC_UNITS -> PropagateVariableTypesInLibraryTask
@@ -184,6 +187,7 @@ digraph G {
184187
READY_LIBRARY_ELEMENT6 -> ReadyLibraryElement6Task
185188
READY_LIBRARY_ELEMENT6 [shape=box]
186189
READY_RESOLVED_UNIT -> ReadyResolvedUnitTask
190+
READY_RESOLVED_UNIT -> ResolveLibraryTask
187191
READY_RESOLVED_UNIT -> VerifyUnitTask
188192
READY_RESOLVED_UNIT [shape=box]
189193
READY_RESOLVED_UNIT10 -> ReadyResolvedUnit10Task
@@ -249,8 +253,9 @@ digraph G {
249253
ReadyResolvedUnit11Task -> READY_RESOLVED_UNIT11
250254
ReadyResolvedUnitTask -> READY_RESOLVED_UNIT
251255
ResolveInstanceFieldsInUnitTask -> RESOLVED_UNIT8
252-
ResolveLibraryReferencesTask -> LIBRARY_ELEMENT
256+
ResolveLibraryReferencesTask -> LIBRARY_ELEMENT8
253257
ResolveLibraryReferencesTask -> REFERENCED_NAMES
258+
ResolveLibraryTask -> LIBRARY_ELEMENT
254259
ResolveLibraryTypeNamesTask -> LIBRARY_ELEMENT5
255260
ResolveUnitTask -> RESOLVED_UNIT10
256261
ResolveUnitTask -> RESOLVE_UNIT_ERRORS

0 commit comments

Comments
 (0)