Index: pkg/compiler/lib/src/dart_backend/renamer.dart |
diff --git a/pkg/compiler/lib/src/dart_backend/renamer.dart b/pkg/compiler/lib/src/dart_backend/renamer.dart |
deleted file mode 100644 |
index 414737e2ea38ab7de84f6feaff5444f20ad427ec..0000000000000000000000000000000000000000 |
--- a/pkg/compiler/lib/src/dart_backend/renamer.dart |
+++ /dev/null |
@@ -1,362 +0,0 @@ |
-// Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
-// for details. All rights reserved. Use of this source code is governed by a |
-// BSD-style license that can be found in the LICENSE file. |
- |
-part of dart_backend; |
- |
-Comparator get _compareNodes => |
- compareBy((n) => n.getBeginToken().charOffset); |
- |
-abstract class Renamable implements Comparable { |
- final int RENAMABLE_TYPE_ELEMENT = 1; |
- final int RENAMABLE_TYPE_MEMBER = 2; |
- final int RENAMABLE_TYPE_LOCAL = 3; |
- |
- final Set<Node> nodes; |
- |
- Renamable(this.nodes); |
- int compareTo(Renamable other) { |
- int nodesDiff = other.nodes.length.compareTo(this.nodes.length); |
- if (nodesDiff != 0) return nodesDiff; |
- int typeDiff = this.kind.compareTo(other.kind); |
- return typeDiff != 0 ? typeDiff : compareInternals(other); |
- } |
- |
- int compareInternals(Renamable other); |
- int get kind; |
- |
- String createNewName(PlaceholderRenamer placeholderRenamer); |
-} |
- |
-class GlobalRenamable extends Renamable { |
- final Entity entity; |
- |
- GlobalRenamable(this.entity, Set<Node> nodes) |
- : super(nodes); |
- |
- int compareInternals(GlobalRenamable other) => |
- compareElements(this.entity, other.entity); |
- int get kind => RENAMABLE_TYPE_ELEMENT; |
- String createNewName(PlaceholderRenamer placeholderRenamer) { |
- return placeholderRenamer._renameGlobal(entity); |
- } |
-} |
- |
-class MemberRenamable extends Renamable { |
- final String identifier; |
- MemberRenamable(this.identifier, Set<Node> nodes) |
- : super(nodes); |
- int compareInternals(MemberRenamable other) => |
- this.identifier.compareTo(other.identifier); |
- int get kind => RENAMABLE_TYPE_MEMBER; |
- String createNewName(PlaceholderRenamer placeholderRenamer) { |
- return placeholderRenamer._generateMemberName(identifier); |
- } |
-} |
- |
-class LocalRenamable extends Renamable { |
- LocalRenamable(Set<Node> nodes) |
- : super(nodes); |
- int compareInternals(LocalRenamable other) => |
- _compareNodes(sorted(this.nodes, _compareNodes)[0], |
- sorted(other.nodes, _compareNodes)[0]); |
- int get kind => RENAMABLE_TYPE_LOCAL; |
- String createNewName(PlaceholderRenamer placeholderRenamer) { |
- return placeholderRenamer._generateUniqueTopLevelName(""); |
- } |
-} |
- |
-/** |
- * Renames only top-level elements that would lead to ambiguity if not renamed. |
- */ |
-class PlaceholderRenamer { |
- /// After running [computeRenames] this will contain the computed renames. |
- final Map<Node, String> renames = new Map<Node, String>(); |
- /// After running [computeRenames] this will contain the used platform |
- /// libraries. |
- final Set<LibraryElement> platformImports = new Set<LibraryElement>(); |
- |
- final bool enableMinification; |
- final Set<String> fixedMemberNames; |
- final Map<Element, LibraryElement> reexportingLibraries; |
- final bool cutDeclarationTypes; |
- |
- final Map<Entity, String> _renamedCache = new Map<Entity, String>(); |
- final Map<Entity, Map<String, String>> _privateCache = |
- new Map<Entity, Map<String, String>>(); |
- |
- // Identifiers that has already been used, or are reserved by the |
- // language/platform. |
- Set<String> _forbiddenIdentifiers; |
- Set<String> _allNamedParameterIdentifiers; |
- |
- Generator _generator; |
- |
- PlaceholderRenamer(this.fixedMemberNames, |
- this.reexportingLibraries, |
- {this.enableMinification, this.cutDeclarationTypes}); |
- |
- void _renameNodes(Iterable<Node> nodes, String renamer(Node node)) { |
- for (Node node in sorted(nodes, _compareNodes)) { |
- renames[node] = renamer(node); |
- } |
- } |
- |
- String _generateUniqueTopLevelName(originalName) { |
- String newName = _generator.generate(originalName, (name) { |
- return _forbiddenIdentifiers.contains(name) || |
- _allNamedParameterIdentifiers.contains(name); |
- }); |
- _forbiddenIdentifiers.add(newName); |
- return newName; |
- } |
- |
- String _generateMemberName(String original) { |
- return _generator.generate(original, _forbiddenIdentifiers.contains); |
- } |
- |
- /// Looks up [originalName] in the [_privateCache] cache of [library]. |
- /// If [originalName] was not renamed before, generate a new name. |
- String _getPrivateName(LibraryElement library, String originalName) { |
- return _privateCache.putIfAbsent(library, () => new Map<String, String>()) |
- .putIfAbsent(originalName, |
- () => _generateUniqueTopLevelName(originalName)); |
- } |
- |
- String _renameConstructor(ConstructorPlaceholder placeholder) { |
- String name = placeholder.element.name; |
- if (name == '') return ""; |
- String result = _renameGlobal(placeholder.element); |
- return result; |
- } |
- |
- String _renameGlobal(Entity entity) { |
- assert(entity is! Element || |
- Elements.isErroneousElement(entity) || |
- Elements.isStaticOrTopLevel(entity) || |
- entity is TypeVariableElement); |
- // TODO(smok): We may want to reuse class static field and method names. |
- if (entity is Element) { |
- LibraryElement library = entity.library; |
- if (reexportingLibraries.containsKey(entity)) { |
- library = reexportingLibraries[entity]; |
- } |
- if (library.isPlatformLibrary) { |
- if (library.canonicalUri != Compiler.DART_CORE) { |
- platformImports.add(library); |
- } |
- if (library.isInternalLibrary) { |
- throw new SpannableAssertionFailure(entity, |
- "Internal library $library should never have been imported from " |
- "the code compiled by dart2dart."); |
- } |
- return entity.name; |
- } |
- } |
- String name = _renamedCache.putIfAbsent(entity, |
- () => _generateUniqueTopLevelName(entity.name)); |
- // Look up in [_renamedCache] for a name for [entity] . |
- // If it was not renamed before, generate a new name. |
- return name; |
- } |
- |
- void _computeMinifiedRenames(PlaceholderCollector placeholderCollector) { |
- _generator = new MinifyingGenerator(); |
- |
- // Build a list sorted by usage of local nodes that will be renamed to |
- // the same identifier. So the top-used local variables in all functions |
- // will be renamed first and will all share the same new identifier. |
- int maxLength = placeholderCollector.functionScopes.values.fold(0, |
- (a, b) => max(a, b.localPlaceholders.length)); |
- |
- List<Set<Node>> allLocals = new List<Set<Node>> |
- .generate(maxLength, (_) => new Set<Node>()); |
- |
- for (FunctionScope functionScope |
- in placeholderCollector.functionScopes.values) { |
- // Add current sorted local identifiers to the whole sorted list |
- // of all local identifiers for all functions. |
- List<LocalPlaceholder> currentSortedPlaceholders = |
- sorted(functionScope.localPlaceholders, |
- compareBy((LocalPlaceholder ph) => -ph.nodes.length)); |
- |
- List<Set<Node>> currentSortedNodes = currentSortedPlaceholders |
- .map((LocalPlaceholder ph) => ph.nodes).toList(); |
- |
- for (int i = 0; i < currentSortedNodes.length; i++) { |
- allLocals[i].addAll(currentSortedNodes[i]); |
- } |
- } |
- |
- // Rename elements, members and locals together based on their usage |
- // count, otherwise when we rename elements first there will be no good |
- // identifiers left for members even if they are used often. |
- List<Renamable> renamables = new List<Renamable>(); |
- placeholderCollector.elementNodes.forEach( |
- (Element element, Set<Node> nodes) { |
- renamables.add(new GlobalRenamable(element, nodes)); |
- }); |
- placeholderCollector.memberPlaceholders.forEach( |
- (String memberName, Set<Identifier> identifiers) { |
- renamables.add(new MemberRenamable(memberName, identifiers)); |
- }); |
- for (Set<Node> localIdentifiers in allLocals) { |
- renamables.add(new LocalRenamable(localIdentifiers)); |
- } |
- renamables.sort(); |
- for (Renamable renamable in renamables) { |
- String newName = renamable.createNewName(this); |
- _renameNodes(renamable.nodes, (_) => newName); |
- } |
- } |
- |
- void _computeNonMinifiedRenames(PlaceholderCollector placeholderCollector) { |
- _generator = new ConservativeGenerator(); |
- // Rename elements. |
- placeholderCollector.elementNodes.forEach( |
- (Element element, Set<Node> nodes) { |
- _renameNodes(nodes, (_) => _renameGlobal(element)); |
- }); |
- |
- // Rename locals. |
- placeholderCollector.functionScopes.forEach( |
- (functionElement, functionScope) { |
- |
- Set<String> memberIdentifiers = new Set<String>(); |
- Set<LocalPlaceholder> placeholders = functionScope.localPlaceholders; |
- if (functionElement.enclosingClass != null) { |
- functionElement.enclosingClass.forEachMember( |
- (enclosingClass, member) { |
- memberIdentifiers.add(member.name); |
- }); |
- } |
- Set<String> usedLocalIdentifiers = new Set<String>(); |
- for (LocalPlaceholder placeholder in placeholders) { |
- String nextId = _generator.generate(placeholder.identifier, (name) { |
- return functionScope.parameterIdentifiers.contains(name) |
- || _forbiddenIdentifiers.contains(name) |
- || usedLocalIdentifiers.contains(name) |
- || memberIdentifiers.contains(name); |
- }); |
- usedLocalIdentifiers.add(nextId); |
- _renameNodes(placeholder.nodes, (_) => nextId); |
- } |
- }); |
- |
- // Do not rename members to top-levels, that allows to avoid renaming |
- // members to constructors. |
- placeholderCollector.memberPlaceholders.forEach((identifier, nodes) { |
- String newIdentifier = _generateMemberName(identifier); |
- _renameNodes(nodes, (_) => newIdentifier); |
- }); |
- } |
- |
- /// Finds renamings for all the placeholders in [placeholderCollector] and |
- /// stores them in [renames]. |
- /// Also adds to [platformImports] all the platform-libraries that are used. |
- void computeRenames(PlaceholderCollector placeholderCollector) { |
- _allNamedParameterIdentifiers = new Set<String>(); |
- for (FunctionScope functionScope in |
- placeholderCollector.functionScopes.values) { |
- _allNamedParameterIdentifiers.addAll(functionScope.parameterIdentifiers); |
- } |
- |
- _forbiddenIdentifiers = new Set<String>.from(fixedMemberNames); |
- _forbiddenIdentifiers.addAll(Keyword.keywords.keys); |
- _forbiddenIdentifiers.add('main'); |
- |
- if (enableMinification) { |
- _computeMinifiedRenames(placeholderCollector); |
- } else { |
- _computeNonMinifiedRenames(placeholderCollector); |
- } |
- |
- // Rename constructors. |
- for (ConstructorPlaceholder placeholder in |
- placeholderCollector.constructorPlaceholders) { |
- renames[placeholder.node] = |
- _renameConstructor(placeholder); |
- }; |
- |
- // Rename private identifiers uniquely for each library. |
- placeholderCollector.privateNodes.forEach( |
- (LibraryElement library, Set<Identifier> identifiers) { |
- for (Identifier identifier in identifiers) { |
- renames[identifier] = _getPrivateName(library, identifier.source); |
- } |
- }); |
- |
- // Rename unresolved nodes, to make sure they still do not resolve. |
- for (Node node in placeholderCollector.unresolvedNodes) { |
- renames[node] = _generateUniqueTopLevelName('Unresolved'); |
- } |
- |
- // Erase prefixes that are now not needed. |
- for (Node node in placeholderCollector.prefixNodesToErase) { |
- renames[node] = ''; |
- } |
- |
- if (cutDeclarationTypes) { |
- for (DeclarationTypePlaceholder placeholder in |
- placeholderCollector.declarationTypePlaceholders) { |
- renames[placeholder.typeNode] = placeholder.requiresVar ? 'var' : ''; |
- } |
- } |
- } |
-} |
- |
-/** |
- * Generates mini ID based on index. |
- * In other words, it converts index to visual representation |
- * as if digits are given characters. |
- */ |
-String generateMiniId(int index) { |
- const String firstCharAlphabet = |
- r'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'; |
- const String otherCharsAlphabet = |
- r'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_$'; |
- // It's like converting index in decimal to [chars] radix. |
- if (index < firstCharAlphabet.length) return firstCharAlphabet[index]; |
- StringBuffer resultBuilder = new StringBuffer(); |
- resultBuilder.writeCharCode( |
- firstCharAlphabet.codeUnitAt(index % firstCharAlphabet.length)); |
- index ~/= firstCharAlphabet.length; |
- int length = otherCharsAlphabet.length; |
- while (index >= length) { |
- resultBuilder.writeCharCode(otherCharsAlphabet.codeUnitAt(index % length)); |
- index ~/= length; |
- } |
- resultBuilder.write(otherCharsAlphabet[index]); |
- return resultBuilder.toString(); |
-} |
- |
-abstract class Generator { |
- String generate(String originalName, bool isForbidden(String name)); |
-} |
- |
-/// Always tries to return original identifier name unless it is forbidden. |
-class ConservativeGenerator implements Generator { |
- String generate(String originalName, bool isForbidden(String name)) { |
- String result = originalName; |
- int index = 0; |
- while (isForbidden(result) ){ //|| result == originalName) { |
- result = '${originalName}_${generateMiniId(index++)}'; |
- } |
- return result; |
- } |
-} |
- |
-/// Always tries to generate the most compact identifier. |
-class MinifyingGenerator implements Generator { |
- int index = 0; |
- |
- MinifyingGenerator(); |
- |
- String generate(String originalName, bool isForbidden(String name)) { |
- String result; |
- do { |
- result = generateMiniId(index++); |
- } while (isForbidden(result)); |
- return result; |
- } |
-} |