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

Side by Side Diff: sdk/lib/_internal/compiler/implementation/js_backend/native_emitter.dart

Issue 11413136: Revert "Generate native class metadata as a JavaScript AST." (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 8 years, 1 month 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
« no previous file with comments | « sdk/lib/_internal/compiler/implementation/js_backend/js_backend.dart ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file 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 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. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 part of js_backend; 5 part of js_backend;
6 6
7 class NativeEmitter { 7 class NativeEmitter {
8 8
9 CodeEmitterTask emitter; 9 CodeEmitterTask emitter;
10 CodeBuffer nativeBuffer; 10 CodeBuffer nativeBuffer;
(...skipping 303 matching lines...) Expand 10 before | Expand all | Expand 10 after
314 // The sets could be much smaller if we could make assumptions about the 314 // The sets could be much smaller if we could make assumptions about the
315 // cls tags of other classes (which are constructor names or part of the 315 // cls tags of other classes (which are constructor names or part of the
316 // result of Object.protocls.toString). For example, if objects that are 316 // result of Object.protocls.toString). For example, if objects that are
317 // Dart objects could be easily excluded, then we might be able to simplify 317 // Dart objects could be easily excluded, then we might be able to simplify
318 // the test, replacing dozens of HTMLxxxElement classes with the regexp 318 // the test, replacing dozens of HTMLxxxElement classes with the regexp
319 // /HTML.*Element/. 319 // /HTML.*Element/.
320 320
321 // Temporary variables for common substrings. 321 // Temporary variables for common substrings.
322 List<String> varNames = <String>[]; 322 List<String> varNames = <String>[];
323 // var -> expression 323 // var -> expression
324 Map<String, js.Expression> varDefns = <String, js.Expression>{}; 324 Map<String, String> varDefns = <String, String>{};
325 // tag -> expression (a string or a variable) 325 // tag -> expression (a string or a variable)
326 Map<ClassElement, js.Expression> tagDefns = 326 Map<ClassElement, String> tagDefns = new Map<ClassElement, String>();
327 new Map<ClassElement, js.Expression>();
328 327
329 String makeExpression(ClassElement classElement) { 328 String makeExpression(ClassElement classElement) {
330 // Expression fragments for this set of cls keys. 329 // Expression fragments for this set of cls keys.
331 List<js.Expression> expressions = <js.Expression>[]; 330 List<String> expressions = <String>[];
332 // TODO: Remove if cls is abstract. 331 // TODO: Remove if cls is abstract.
333 List<String> subtags = [toNativeName(classElement)]; 332 List<String> subtags = [toNativeName(classElement)];
334 void walk(ClassElement cls) { 333 void walk(ClassElement cls) {
335 for (final ClassElement subclass in getDirectSubclasses(cls)) { 334 for (final ClassElement subclass in getDirectSubclasses(cls)) {
336 ClassElement tag = subclass; 335 ClassElement tag = subclass;
337 String existing = tagDefns[tag]; 336 String existing = tagDefns[tag];
338 if (existing == null) { 337 if (existing == null) {
339 subtags.add(toNativeName(tag)); 338 subtags.add(toNativeName(tag));
340 walk(subclass); 339 walk(subclass);
341 } else { 340 } else {
342 if (varDefns.containsKey(existing)) { 341 if (varDefns.containsKey(existing)) {
343 expressions.add(existing); 342 expressions.add(existing);
344 } else { 343 } else {
345 String varName = 'v${varNames.length}_${tag.name.slowToString()}'; 344 String varName = 'v${varNames.length}/*${tag}*/';
346 varNames.add(varName); 345 varNames.add(varName);
347 varDefns[varName] = existing; 346 varDefns[varName] = existing;
348 tagDefns[tag] = new js.VariableUse(varName); 347 tagDefns[tag] = varName;
349 expressions.add(new js.VariableUse(varName)); 348 expressions.add(varName);
350 } 349 }
351 } 350 }
352 } 351 }
353 } 352 }
354 walk(classElement); 353 walk(classElement);
355 if (!subtags.isEmpty) { 354 String constantPart = "'${Strings.join(subtags, '|')}'";
356 expressions.add( 355 if (constantPart != "''") expressions.add(constantPart);
357 new js.LiteralString("'${Strings.join(subtags, '|')}'")); 356 String expression;
358 }
359 js.Expression expression;
360 if (expressions.length == 1) { 357 if (expressions.length == 1) {
361 expression = expressions[0]; 358 expression = expressions[0];
362 } else { 359 } else {
363 js.Expression array = new js.ArrayInitializer.from(expressions); 360 expression = "[${Strings.join(expressions, ',')}].join('|')";
364 expression = new js.Call(
365 new js.PropertyAccess.field(array, 'join'),
366 [new js.LiteralString("'|'")]);
367 } 361 }
368 return expression; 362 return expression;
369 } 363 }
370 364
371 for (final ClassElement classElement in dispatchClasses) { 365 for (final ClassElement classElement in dispatchClasses) {
372 tagDefns[classElement] = makeExpression(classElement); 366 tagDefns[classElement] = makeExpression(classElement);
373 } 367 }
374 368
375 // Write out a thunk that builds the metadata. 369 // Write out a thunk that builds the metadata.
376 if (!tagDefns.isEmpty) { 370 if (!tagDefns.isEmpty) {
377 List<js.Statement> statements = <js.Statement>[]; 371 nativeBuffer.add('(function(){\n');
378 List<js.Expression> initializations = <js.Expression>[]; 372
379 for (final String varName in varNames) { 373 for (final String varName in varNames) {
380 initializations.add( 374 nativeBuffer.add(' var ${varName} = ${varDefns[varName]};\n');
381 new js.VariableInitialization(
382 new js.VariableDeclaration(varName),
383 varDefns[varName]));
384 } 375 }
385 376
386 statements.add( 377 nativeBuffer.add(' var table = [\n');
387 new js.ExpressionStatement( 378 nativeBuffer.add(
388 new js.VariableDeclarationList(initializations))); 379 ' // [dynamic-dispatch-tag, '
380 'tags of classes implementing dynamic-dispatch-tag]');
381 bool needsComma = false;
382 List<String> entries = <String>[];
383 for (final ClassElement cls in dispatchClasses) {
384 String clsName = toNativeName(cls);
385 entries.add("\n ['$clsName', ${tagDefns[cls]}]");
386 }
387 nativeBuffer.add(Strings.join(entries, ','));
388 nativeBuffer.add('];\n');
389 nativeBuffer.add('$dynamicSetMetadataName(table);\n');
389 390
390 // [table] is a list of lists, each inner list of the form: 391 nativeBuffer.add('})();\n');
391 // [dynamic-dispatch-tag, tags-of-classes-implementing-dispatch-tag]
392 // E.g.
393 // [['Node', 'Text|HTMLElement|HTMLDivElement|...'], ...]
394 js.Expression table =
395 new js.ArrayInitializer.from(
396 dispatchClasses.map((cls) =>
397 new js.ArrayInitializer.from([
398 new js.LiteralString("'${toNativeName(cls)}'"),
399 tagDefns[cls]])));
400
401 // $.dynamicSetMetadata(table);
402 statements.add(
403 new js.ExpressionStatement(
404 new js.Call(
405 new js.VariableUse(dynamicSetMetadataName),
406 [table])));
407
408 // (function(){statements})();
409 nativeBuffer.add(
410 js.prettyPrint(
411 new js.ExpressionStatement(
412 new js.Call(new js.Fun([], new js.Block(statements)), [])),
413 compiler));
414 } 392 }
415 } 393 }
416 394
417 bool isSupertypeOfNativeClass(Element element) { 395 bool isSupertypeOfNativeClass(Element element) {
418 if (element.isTypeVariable()) { 396 if (element.isTypeVariable()) {
419 compiler.cancel("Is check for type variable", element: element); 397 compiler.cancel("Is check for type variable", element: element);
420 return false; 398 return false;
421 } 399 }
422 if (element.computeType(compiler).unalias(compiler) is FunctionType) { 400 if (element.computeType(compiler).unalias(compiler) is FunctionType) {
423 // The element type is a function type either directly or through 401 // The element type is a function type either directly or through
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after
497 if (!first) targetBuffer.add(",\n"); 475 if (!first) targetBuffer.add(",\n");
498 targetBuffer.add(" $name: $function"); 476 targetBuffer.add(" $name: $function");
499 first = false; 477 first = false;
500 }); 478 });
501 targetBuffer.add("\n});\n\n"); 479 targetBuffer.add("\n});\n\n");
502 } 480 }
503 targetBuffer.add(nativeBuffer); 481 targetBuffer.add(nativeBuffer);
504 targetBuffer.add('\n'); 482 targetBuffer.add('\n');
505 } 483 }
506 } 484 }
OLDNEW
« no previous file with comments | « sdk/lib/_internal/compiler/implementation/js_backend/js_backend.dart ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698