Skip to content

Commit 7a2f1ad

Browse files
nshahancommit-bot@chromium.org
authored andcommitted
[ddc] Add function symbol information
- Collects `FunctionSymbols` for top level functions, getters, setters, as well as class methods, getters and setters. - Add test cases. Change-Id: If26c59e920c3e6e914c7f06e3b725afdf048c4e1 Issue: #40273 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/207100 Reviewed-by: Anna Gringauze <[email protected]> Commit-Queue: Nicholas Shahan <[email protected]>
1 parent 7b0b865 commit 7a2f1ad

File tree

5 files changed

+770
-20
lines changed

5 files changed

+770
-20
lines changed

pkg/dev_compiler/lib/src/kernel/command.dart

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -748,13 +748,17 @@ ModuleSymbols _emitSymbols(ProgramCompiler compiler, String moduleName,
748748
for (var e in compiler.classIdentifiers.entries)
749749
e.key: identifierNames[e.value],
750750
};
751+
var procedureJsNames = <Procedure, String>{
752+
for (var e in compiler.procedureIdentifiers.entries)
753+
e.key: identifierNames[e.value],
754+
};
751755
var variableJsNames = <VariableDeclaration, String>{
752756
for (var e in compiler.variableIdentifiers.entries)
753757
e.key: identifierNames[e.value],
754758
};
755759

756-
return ModuleSymbolsCollector(
757-
moduleName, classJsNames, compiler.memberNames, variableJsNames)
760+
return ModuleSymbolsCollector(moduleName, classJsNames, compiler.memberNames,
761+
procedureJsNames, variableJsNames)
758762
.collectSymbolInfo(component);
759763
}
760764

pkg/dev_compiler/lib/src/kernel/compiler.dart

Lines changed: 25 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,13 @@ class ProgramCompiler extends ComputeOnceConstantVisitor<js_ast.Expression>
6161
/// module.
6262
final memberNames = <Member, String>{};
6363

64+
/// Maps each `Procedure` node compiled in the module to the `Identifier`s
65+
/// used to name the class in JavaScript.
66+
///
67+
/// This mapping is used when generating the symbol information for the
68+
/// module.
69+
final procedureIdentifiers = <Procedure, js_ast.Identifier>{};
70+
6471
/// Maps each `VariableDeclaration` node compiled in the module to the name
6572
/// used for the variable in JavaScript.
6673
///
@@ -2368,8 +2375,9 @@ class ProgramCompiler extends ComputeOnceConstantVisitor<js_ast.Expression>
23682375
Class memberClass}) {
23692376
// Static members skip the rename steps and may require JS interop renames.
23702377
if (isStatic) {
2371-
// TODO(nshahan) Record the name for this member in memberNames.
2372-
return _emitStaticMemberName(name, member);
2378+
var memberName = _emitStaticMemberName(name, member);
2379+
memberNames[member] = memberName.valueWithoutQuotes;
2380+
return memberName;
23732381
}
23742382

23752383
// We allow some (illegal in Dart) member names to be used in our private
@@ -2379,6 +2387,7 @@ class ProgramCompiler extends ComputeOnceConstantVisitor<js_ast.Expression>
23792387
var runtimeName = _jsExportName(member);
23802388
if (runtimeName != null) {
23812389
var parts = runtimeName.split('.');
2390+
// TODO(nshahan) Record the name for this member in memberNames.
23822391
if (parts.length < 2) return propertyName(runtimeName);
23832392

23842393
js_ast.Expression result = _emitIdentifier(parts[0]);
@@ -2652,8 +2661,9 @@ class ProgramCompiler extends ComputeOnceConstantVisitor<js_ast.Expression>
26522661
_currentUri = node.fileUri;
26532662

26542663
var name = node.name.text;
2664+
memberNames[node] = name;
26552665
var result = js_ast.Method(
2656-
propertyName(name), _emitFunction(node.function, node.name.text),
2666+
propertyName(name), _emitFunction(node.function, name),
26572667
isGetter: node.isGetter, isSetter: node.isSetter)
26582668
..sourceInformation = _nodeEnd(node.fileEndOffset);
26592669

@@ -2678,8 +2688,10 @@ class ProgramCompiler extends ComputeOnceConstantVisitor<js_ast.Expression>
26782688

26792689
var nameExpr = _emitTopLevelName(p);
26802690
var jsName = _safeFunctionNameForSafari(p.name.text, fn);
2681-
body.add(js.statement('# = #',
2682-
[nameExpr, js_ast.NamedFunction(_emitTemporaryId(jsName), fn)]));
2691+
var functionName = _emitTemporaryId(jsName);
2692+
procedureIdentifiers[p] = functionName;
2693+
body.add(js.statement(
2694+
'# = #', [nameExpr, js_ast.NamedFunction(functionName, fn)]));
26832695

26842696
_currentUri = savedUri;
26852697
_staticTypeContext.leaveMember(p);
@@ -3605,7 +3617,7 @@ class ProgramCompiler extends ComputeOnceConstantVisitor<js_ast.Expression>
36053617
}
36063618

36073619
for (var p in f.positionalParameters) {
3608-
var jsParam = _emitVariableDef(p);
3620+
var jsParam = _emitVariableRef(p);
36093621
if (_checkParameters) {
36103622
initParameter(p, jsParam);
36113623
}
@@ -4510,21 +4522,19 @@ class ProgramCompiler extends ComputeOnceConstantVisitor<js_ast.Expression>
45104522
var name = v.name;
45114523
if (name == null || name.startsWith('#')) {
45124524
name = name == null ? 't${_tempVariables.length}' : name.substring(1);
4513-
// TODO(nshahan) Record the Identifier for this variable in
4514-
// variableIdentifiers.
45154525
return _tempVariables.putIfAbsent(v, () => _emitTemporaryId(name));
45164526
}
4517-
var identifier = _emitIdentifier(name);
4518-
variableIdentifiers[v] = identifier;
4519-
return identifier;
4527+
return _emitIdentifier(name);
45204528
}
45214529

45224530
/// Emits the declaration of a variable.
45234531
///
45244532
/// This is similar to [_emitVariableRef] but it also attaches source
45254533
/// location information, so hover will work as expected.
45264534
js_ast.Identifier _emitVariableDef(VariableDeclaration v) {
4527-
return _emitVariableRef(v)..sourceInformation = _nodeStart(v);
4535+
var identifier = _emitVariableRef(v)..sourceInformation = _nodeStart(v);
4536+
variableIdentifiers[v] = identifier;
4537+
return identifier;
45284538
}
45294539

45304540
js_ast.Statement _initLetVariables() {
@@ -6403,8 +6413,9 @@ class ProgramCompiler extends ComputeOnceConstantVisitor<js_ast.Expression>
64036413
Library library, String className, Member member,
64046414
[js_ast.TemporaryId id]) {
64056415
var name = '$className.${member.name.text}';
6406-
// Names used in the symbols for the public fields
6407-
// memberNames[member] = 'Symbol($name)';
6416+
// Wrap the name as a symbol here so it matches what you would find at
6417+
// runtime when you get all properties and symbols from an instance.
6418+
memberNames[member] = 'Symbol($name)';
64086419
return emitPrivateNameSymbol(library, name, id);
64096420
}
64106421

pkg/dev_compiler/lib/src/kernel/module_symbols_collector.dart

Lines changed: 25 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,21 +14,23 @@ class ModuleSymbolsCollector extends RecursiveVisitor {
1414
/// The first scope added to the stack should always be the library scope. The
1515
/// last element in the list represents the current scope.
1616
final _scopes = <ScopeSymbol>[];
17+
1718
final ModuleSymbols _moduleSymbols;
1819
final Map<Class, String> _classJsNames;
1920
final Map<Member, String> _memberJsNames;
21+
final Map<Procedure, String> _procedureJsNames;
2022
final Map<VariableDeclaration, String> _variableJsNames;
2123

2224
ModuleSymbolsCollector(String moduleName, this._classJsNames,
23-
this._memberJsNames, this._variableJsNames)
25+
this._memberJsNames, this._procedureJsNames, this._variableJsNames)
2426
: _moduleSymbols = ModuleSymbols(
2527
version: ModuleSymbols.current.version,
2628
moduleName: moduleName,
2729
libraries: <LibrarySymbol>[],
2830
scripts: <Script>[],
2931
classes: <ClassSymbol>[],
3032
// TODO(nshahan) functionTypes
31-
// TODO(nshahan) functions
33+
functions: <FunctionSymbol>[],
3234
// TODO(nshahan) scopes
3335
variables: <VariableSymbol>[]);
3436

@@ -142,8 +144,27 @@ class ModuleSymbolsCollector extends RecursiveVisitor {
142144
// Legacy libraries contain procedures with no bodies for all Object methods
143145
// in every class. We can ignore these unless they actually contain a body.
144146
if (node.function.body == null) return;
145-
// TODO(nshahan) implement visitProcedure
146-
super.visitProcedure(node);
147+
var functionSymbol = FunctionSymbol(
148+
name: node.name.text,
149+
// TODO(nshahan) typeId - probably should canonicalize but keep original
150+
// type argument names.
151+
isStatic: node.isStatic,
152+
isConst: node.isConst,
153+
localId: _memberJsNames[node] ?? _procedureJsNames[node],
154+
scopeId: _scopes.last.id,
155+
variableIds: <String>[],
156+
scopeIds: <String>[],
157+
location: SourceLocation(
158+
scriptId: _scriptId(node.location.file),
159+
tokenPos: node.fileOffset,
160+
endTokenPos: node.fileEndOffset));
161+
162+
_scopes.add(functionSymbol);
163+
node.visitChildren(this);
164+
_scopes
165+
..removeLast()
166+
..last.scopeIds.add(functionSymbol.id);
167+
_moduleSymbols.functions.add(functionSymbol);
147168
}
148169

149170
@override

0 commit comments

Comments
 (0)