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

Unified Diff: pkg/compiler/lib/src/universe/universe.dart

Issue 1182913003: Split TypedSelector into Selector and TypeMask. (Closed) Base URL: https://github.com/dart-lang/sdk.git@master
Patch Set: Updated cf. comments. Created 5 years, 6 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « pkg/compiler/lib/src/universe/function_set.dart ('k') | pkg/compiler/lib/src/use_unused_api.dart » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: pkg/compiler/lib/src/universe/universe.dart
diff --git a/pkg/compiler/lib/src/universe/universe.dart b/pkg/compiler/lib/src/universe/universe.dart
index 0ae3cb6906c4ce5657afd8e76bf10b0f1c9472a9..8af776327ee76c2076205e910b6ce06ba9ed8eb6 100644
--- a/pkg/compiler/lib/src/universe/universe.dart
+++ b/pkg/compiler/lib/src/universe/universe.dart
@@ -14,6 +14,72 @@ import '../util/util.dart';
part 'function_set.dart';
part 'side_effects.dart';
+class UniverseSelector {
+ final Selector selector;
+ final TypeMask mask;
+
+ UniverseSelector(this.selector, this.mask);
+
+ bool appliesUnnamed(Element element, ClassWorld world) {
+ return selector.appliesUnnamed(element, world) &&
+ (mask == null || mask.canHit(element, selector, world));
+ }
+
+ String toString() => '$selector,$mask';
+}
+
+abstract class TypeMaskSet {
+ bool applies(Element element, Selector selector, ClassWorld world);
+ Iterable<TypeMask> get masks;
+}
+
+/// An implementation of a [TypeMaskSet] that is only increasing, that is, once
+/// a mask is added it cannot be removed.
+class IncreasingTypeMaskSet extends TypeMaskSet {
+ bool isAll = false;
+ Set<TypeMask> _masks;
+
+ bool applies(Element element, Selector selector, ClassWorld world) {
+ if (isAll) return true;
+ if (_masks == null) return false;
+ for (TypeMask mask in _masks) {
+ if (mask.canHit(element, selector, world)) return true;
+ }
+ return false;
+ }
+
+ bool add(TypeMask mask) {
+ if (isAll) return false;
+ if (mask == null) {
+ isAll = true;
+ _masks = null;
+ return true;
+ }
+ if (_masks == null) {
+ _masks = new Setlet<TypeMask>();
+ }
+ return _masks.add(mask);
+ }
+
+ Iterable<TypeMask> get masks {
+ if (isAll) return const [null];
+ if (_masks == null) return const [];
+ return _masks;
+ }
+
+ String toString() {
+ if (isAll) {
+ return '<all>';
+ } else if (_masks != null) {
+ return '$_masks';
+ } else {
+ return '<none>';
+ }
+ }
+}
+
+
+
class Universe {
/// The set of all directly instantiated classes, that is, classes with a
/// generative constructor that has been called directly and not only through
@@ -51,12 +117,12 @@ class Universe {
new Set<FunctionElement>();
final Set<FunctionElement> methodsNeedingSuperGetter =
new Set<FunctionElement>();
- final Map<String, Set<Selector>> invokedNames =
- new Map<String, Set<Selector>>();
- final Map<String, Set<Selector>> invokedGetters =
- new Map<String, Set<Selector>>();
- final Map<String, Set<Selector>> invokedSetters =
- new Map<String, Set<Selector>>();
+ final Map<String, Map<Selector, TypeMaskSet>> _invokedNames =
+ <String, Map<Selector, TypeMaskSet>>{};
+ final Map<String, Map<Selector, TypeMaskSet>> _invokedGetters =
+ <String, Map<Selector, TypeMaskSet>>{};
+ final Map<String, Map<Selector, TypeMaskSet>> _invokedSetters =
+ <String, Map<Selector, TypeMaskSet>>{};
/**
* Fields accessed. Currently only the codegen knows this
@@ -159,26 +225,75 @@ class Universe {
});
}
- bool hasMatchingSelector(Set<Selector> selectors,
- Element member,
- World world) {
+ bool _hasMatchingSelector(Map<Selector, TypeMaskSet> selectors,
+ Element member,
+ World world) {
if (selectors == null) return false;
- for (Selector selector in selectors) {
- if (selector.appliesUnnamed(member, world)) return true;
+ for (Selector selector in selectors.keys) {
+ if (selector.appliesUnnamed(member, world)) {
+ TypeMaskSet masks = selectors[selector];
+ if (masks.applies(member, selector, world)) {
+ return true;
+ }
+ }
}
return false;
}
bool hasInvocation(Element member, World world) {
- return hasMatchingSelector(invokedNames[member.name], member, world);
+ return _hasMatchingSelector(_invokedNames[member.name], member, world);
}
bool hasInvokedGetter(Element member, World world) {
- return hasMatchingSelector(invokedGetters[member.name], member, world);
+ return _hasMatchingSelector(_invokedGetters[member.name], member, world);
}
bool hasInvokedSetter(Element member, World world) {
- return hasMatchingSelector(invokedSetters[member.name], member, world);
+ return _hasMatchingSelector(_invokedSetters[member.name], member, world);
+ }
+
+ bool registerInvocation(UniverseSelector selector) {
+ return _registerNewSelector(selector, _invokedNames);
+ }
+
+ bool registerInvokedGetter(UniverseSelector selector) {
+ return _registerNewSelector(selector, _invokedGetters);
+ }
+
+ bool registerInvokedSetter(UniverseSelector selector) {
+ return _registerNewSelector(selector, _invokedSetters);
+ }
+
+ bool _registerNewSelector(
+ UniverseSelector universeSelector,
+ Map<String, Map<Selector, TypeMaskSet>> selectorMap) {
+ Selector selector = universeSelector.selector;
+ String name = selector.name;
+ TypeMask mask = universeSelector.mask;
+ Map<Selector, TypeMaskSet> selectors = selectorMap.putIfAbsent(
+ name, () => new Maplet<Selector, TypeMaskSet>());
+ IncreasingTypeMaskSet masks = selectors.putIfAbsent(
+ selector, () => new IncreasingTypeMaskSet());
+ return masks.add(mask);
+ }
+
+ Map<Selector, TypeMaskSet> invocationsByName(String name) {
+ return _invokedNames[name];
+ }
+
+ void forEachInvokedName(
+ f(String name, Map<Selector, TypeMaskSet> selectors)) {
+ _invokedNames.forEach(f);
+ }
+
+ void forEachInvokedGetter(
+ f(String name, Map<Selector, TypeMaskSet> selectors)) {
+ _invokedGetters.forEach(f);
+ }
+
+ void forEachInvokedSetter(
+ f(String name, Map<Selector, TypeMaskSet> selectors)) {
+ _invokedSetters.forEach(f);
}
DartType registerIsCheck(DartType type, Compiler compiler) {
@@ -568,7 +683,6 @@ class Selector {
Selector existing = list[i];
if (existing.match(kind, name, callStructure)) {
assert(existing.hashCode == hashCode);
- assert(existing.mask == null);
return existing;
}
}
@@ -693,10 +807,6 @@ class Selector {
/** Check whether this is a call to 'assert'. */
bool get isAssert => isCall && identical(name, "assert");
- bool get hasExactMask => false;
- TypeMask get mask => null;
- Selector get asUntyped => this;
-
/**
* The member name for invocation mirrors created from this selector.
*/
@@ -776,84 +886,8 @@ class Selector {
}
String toString() {
- String type = '';
- if (mask != null) type = ', mask=$mask';
- return 'Selector($kind, $name, ${callStructure.structureToString()}$type)';
- }
-
- Selector extendIfReachesAll(Compiler compiler) {
- return new TypedSelector(
- compiler.typesTask.dynamicType, this, compiler.world);
+ return 'Selector($kind, $name, ${callStructure.structureToString()})';
}
Selector toCallSelector() => new Selector.callClosureFrom(this);
}
-
-class TypedSelector extends Selector {
- final Selector asUntyped;
- final TypeMask mask;
-
- TypedSelector.internal(this.mask, Selector selector, int hashCode)
- : asUntyped = selector,
- super.internal(selector.kind,
- selector.memberName,
- selector.callStructure,
- hashCode) {
- assert(mask != null);
- assert(asUntyped.mask == null);
- }
-
-
- factory TypedSelector(TypeMask mask, Selector selector, World world) {
- if (!world.hasClosedWorldAssumption) {
- // TODO(johnniwinther): Improve use of TypedSelector in an open world.
- bool isNullable = mask.isNullable;
- mask = world.compiler.typesTask.dynamicType;
- if (isNullable) {
- mask = mask.nullable();
- }
- }
- // TODO(johnniwinther): Allow more TypeSelector kinds during resoluton.
- assert(world.isClosed || mask.isExact);
- if (selector.mask == mask) return selector;
- Selector untyped = selector.asUntyped;
- Map<TypeMask, TypedSelector> map = world.canonicalizedValues
- .putIfAbsent(untyped, () => new Map<TypeMask, TypedSelector>());
- TypedSelector result = map[mask];
- if (result == null) {
- int hashCode = Hashing.mixHashCodeBits(untyped.hashCode, mask.hashCode);
- result = map[mask] = new TypedSelector.internal(mask, untyped, hashCode);
- }
- return result;
- }
-
- factory TypedSelector.exact(
- ClassElement base, Selector selector, World world)
- => new TypedSelector(new TypeMask.exact(base, world), selector,
- world);
-
- factory TypedSelector.subclass(
- ClassElement base, Selector selector, World world)
- => new TypedSelector(new TypeMask.subclass(base, world),
- selector, world);
-
- factory TypedSelector.subtype(
- ClassElement base, Selector selector, World world)
- => new TypedSelector(new TypeMask.subtype(base, world),
- selector, world);
-
- bool appliesUnnamed(Element element, World world) {
- assert(sameNameHack(element, world));
- if (!mask.canHit(element, this, world)) return false;
- return appliesUntyped(element, world);
- }
-
- Selector extendIfReachesAll(Compiler compiler) {
- bool canReachAll = compiler.enabledInvokeOn
- && mask.needsNoSuchMethodHandling(this, compiler.world);
- return canReachAll
- ? new TypedSelector(
- compiler.typesTask.dynamicType, this, compiler.world)
- : this;
- }
-}
« no previous file with comments | « pkg/compiler/lib/src/universe/function_set.dart ('k') | pkg/compiler/lib/src/use_unused_api.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698