Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(251)

Side by Side Diff: lib/compiler/implementation/dart_backend/placeholder_collector.dart

Issue 10836128: A visitor that builds a map from node to "Usage". (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 8 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file.
4
5 class SendVisitor extends ResolvedVisitor {
6 final PlaceholderCollector collector;
7
8 SendVisitor(this.collector, TreeElements elements) : super(elements);
9
10 visitSuperSend(Send node) {}
11 visitOperatorSend(Send node) {}
12 visitClosureSend(Send node) {}
13 visitDynamicSend(Send node) {}
14 visitForeignSend(Send node) {}
15
16 visitGetterSend(Send node) {
17 final element = elements[node];
18 // element === null means dynamic property access.
Anton Muhin 2012/08/08 08:27:20 what !isTopLevel() means?
Roman 2012/08/09 05:02:35 added comment that we don't want to rename non-top
19 if (element === null || !element.isTopLevel()) return;
20 // Unqualified <class> in static invocation, why it's not a type annotation?
21 // Another option would be to process in visitStaticSend, NB:
22 // those elements are not top-level.
23 // OR: unqualified top level.
24 collector.placeholderForElement(node.selector, element);
Anton Muhin 2012/08/08 08:27:20 nit: placeholderForElement makes me think it shoul
Roman 2012/08/09 05:02:35 Done.
25 if (node.receiver !== null) {
26 // <lib prefix>.<top level>.
27 collector.placeholderForNull(node.receiver); // Cut library prefix.
28 }
29 }
30
31 visitStaticSend(Send node) {
32 final element = elements[node];
33 if (!element.isTopLevel()) return;
34 // Another ugly case: <lib prefix>.<top level> is represented as
35 // receiver: lib prefix, selector: top level.
36 collector.placeholderForMethod(node.selector, element);
37 if (node.receiver !== null) {
38 assert(elements[node.receiver].isPrefix());
39 // Hack: putting null into map overrides receiver of original node.
40 collector.placeholderForNull(node.receiver);
41 }
42 }
43 }
44
45 class PlaceholderCollector extends AbstractVisitor {
46 final Compiler compiler;
47 final Map<Node, Placeholder> placeholders;
48 Element currentElement;
49 TreeElements treeElements;
50
51 PlaceholderCollector(this.compiler) :
52 placeholders = new Map<Node, Placeholder>();
53
54 void processFunction(FunctionElement element, Node node) {
Anton Muhin 2012/08/08 08:27:20 nit: process (here and in the method below) is too
Roman 2012/08/09 05:02:35 Done.
55 if (element.isGenerativeConstructor() || element.isFactoryConstructor()) {
56 // Two complicated cases for class/interface renaming:
57 // 1) class which implements constructors of other interfaces, but not
58 // implements interfaces themselves:
59 // 0.dart: class C { I(); }
60 // 1.dart and 2.dart: interface I default C { I(); }
61 // now we have to duplicate our I() constructor in C class with
62 // proper names.
63 // 2) (even worse for us):
64 // 0.dart: class C { C(); }
65 // 1.dart: interface C default p0.C { C(); }
66 // the second case is just a bug now.
67 final enclosingClass = element.getEnclosingClass();
68 Node nameNode = node.name;
69 if (nameNode is Send) nameNode = nameNode.receiver;
70 // For cases like class C implements I { I(); }
71 if (nameNode.token.slowToString() == enclosingClass.name.slowToString()) {
72 placeholderForType(nameNode, enclosingClass.type);
73 }
74 } else {
75 placeholderForElement(node.name, element);
76 }
77 }
78
79 void process(Element element, TreeElements elements) {
80 if (element.isField()) {
81 // TODO(smok): In the future make sure we don't process same
82 // variable list element twice, better merge this with emitter logic.
83 element = element.variables;
84 }
85 currentElement = element;
86 treeElements = elements;
87 Node elementNode = element.parseNode(compiler);
88 if (element is FunctionElement) {
89 processFunction(element, elementNode);
90 }
91 elementNode.accept(this);
92 }
93
94 Type resolveType(TypeAnnotation typeAnnotation) {
95 if (treeElements === null) return null;
96 var result = treeElements.getType(typeAnnotation);
97 // TODO: Have better type resolution.
98 if (result === null) {
99 result = compiler.resolveTypeAnnotation(currentElement, typeAnnotation);
100 }
101 return result;
102 }
103
104 void placeholderForType(Node node, Type type) {
105 assert(type !== null);
106 placeholders[node] = new TypePlaceholder(type);
107 }
Anton Muhin 2012/08/08 08:27:20 nit: blank lines between methods, please
Roman 2012/08/09 05:02:35 Done.
108 void placeholderForMethod(Node node, Element method) {
109 assert(method !== null);
110 assert(method is FunctionElement || method is VariableElement);
111 placeholders[node] = new MethodPlaceholder(method);
112 }
113 void placeholderForNull(Node node) {
114 placeholders[node] = new NullPlaceholder();
115 }
116 void placeholderForElement(Node node, Element element) {
117 assert(element !== null);
118 placeholders[node] = new ElementPlaceholder(element);
119 }
120
121 void internalError(String reason, [Node node]) {
122 compiler.cancel(reason: reason, node: node);
123 }
124
125 visit(Node node) => (node === null) ? null : node.accept(this);
126 visitNode(Node node) { node.visitChildren(this); } // We must go deeper.
Anton Muhin 2012/08/08 08:27:20 memegen link? :)
127
128 visitClassNode(ClassNode node) {
129 internalError('Should never meet ClassNode', node);
130 }
131
132 visitSend(Send send) {
133 new SendVisitor(this, treeElements).visitSend(send);
134 send.visitChildren(this);
Anton Muhin 2012/08/08 08:27:20 super.visitSend(send)?
Roman 2012/08/09 05:02:35 Done.
135 }
136
137 visitTypeAnnotation(TypeAnnotation node) {
138 final type = compiler.resolveTypeAnnotation(currentElement, node);
139 if (type is !InterfaceType) return null;
140 var target = node.typeName;
141 if (node.typeName is Send) {
142 final element = treeElements[node];
143 if (element !== null) {
144 final send = node.typeName.asSend();
145 final isPrefixed = element.lookupConstructor(
Anton Muhin 2012/08/08 08:27:20 nit: please, rename isPrefixed -> hasPrefix
Roman 2012/08/09 05:02:35 Done.
146 send.receiver.source, send.selector.source) === null;
147 if (!isPrefixed) target = send.receiver;
148 }
149 }
150 placeholderForType(target, type);
151 visit(node.typeArguments);
Anton Muhin 2012/08/08 08:27:20 super.visitTypeAnnotation(node)?
Roman 2012/08/09 05:02:35 Done.
152 }
153 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698