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

Unified Diff: frog/value.dart

Issue 8746005: Fix a bunch of issues with 'hidden' DOM types. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: removed dead code Created 9 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 side-by-side diff with in-line comments
Download patch
Index: frog/value.dart
diff --git a/frog/value.dart b/frog/value.dart
index 09caf66980b62664db70f806b602ff32bbb9fd65..c80b4204dd3ad262e6df0c8473dcf6da1eec2c4b 100644
--- a/frog/value.dart
+++ b/frog/value.dart
@@ -293,7 +293,7 @@ class Value {
// Generate a runtime checks if they're turned on, otherwise skip it.
if (options.enableTypeChecks) {
- return _typeAssert(context, toType, node);
+ return _typeAssert(context, toType, node, isDynamic);
} else {
return this;
}
@@ -331,23 +331,29 @@ class Value {
* [instanceOf], but it allows null since Dart types are nullable.
* Also it will throw a TypeError if it gets the wrong type.
*/
- Value _typeAssert(MethodGenerator context, Type toType, Node node) {
+ Value _typeAssert(MethodGenerator context, Type toType, Node node,
+ bool isDynamic) {
if (toType is ParameterType) {
ParameterType p = toType;
toType = p.extendsType;
}
- // TODO(jmesserly): fix checking of function types, and DOM objects
- // For now, don't generate a broken check.
- // (For DOM types to work right, we need to lazily patch the "is$DOMWindow"
- // check methods, by catching it on Object.prototype like VarMember does)
- if (toType.getCallMethod() != null || toType.library == world.dom) {
- return this;
- }
-
if (toType.isObject || toType.isVar) {
- world.internalError('We thought ${type.name} is not a subtype of ${toType.name}?');
- }
+ world.internalError(
+ 'We thought ${type.name} is not a subtype of ${toType.name}?');
+ }
+
+ final typeError = world.corelib.types['TypeError'];
+ final typeErrorCtor = typeError.getConstructor('_internal');
+ world.gen.corejs.ensureTypeNameOf();
+ final result = typeErrorCtor.invoke(context, node,
+ new Value.type(typeError, null),
+ new Arguments(null, [
+ new Value(world.objectType, 'this', null),
+ new Value(world.stringType, '"${toType.name}"', null)]),
+ isDynamic);
+ world.gen.corejs.useThrow = true;
+ final throwTypeError = '\$throw(${result.code})';
// TODO(jmesserly): better assert for integers?
if (toType.isNum) toType = world.numType;
@@ -364,7 +370,8 @@ class Value {
if (toType.typeCheckCode == null) {
toType.typeCheckCode = '''
function \$assert_void(x) {
- return x == null ? x : x.is\$void(); // throws TypeError
+ if (x == null) return null;
+ $throwTypeError
}''';
}
} else if (toType == world.nonNullBool) {
@@ -379,17 +386,25 @@ function \$assert_void(x) {
toType.typeCheckCode = '''
function \$assert_${toType.name}(x) {
if (x == null || typeof(x) == "${toType.typeofName}") return x;
- throw new TypeError("'" + x + "' is not a ${toType.name}.");
+ $throwTypeError
}''';
}
} else {
- toType.isTested = true;
+ toType.isChecked = true;
+
+ String checkName = 'assert\$' + toType.jsname;
// If we track nullability, we could simplify this check.
var temp = context.getTemp(this);
- check = '(${context.assignTemp(temp, this).code} &&';
- check += ' ${temp.code}.is\$${toType.jsname}())';
+ check = '(${context.assignTemp(temp, this).code} == null ? null :';
+ check += ' ${temp.code}.$checkName())';
if (this != temp) context.freeTemp(temp);
+
+ // Generate the fallback on Object (that throws a TypeError)
+ if (!world.objectType.varStubs.containsKey(checkName)) {
+ world.objectType.varStubs[checkName] =
+ new VarMethodStub(checkName, null, Arguments.EMPTY, throwTypeError);
+ }
}
return new Value(toType, check, span);
@@ -428,7 +443,8 @@ function \$assert_${toType.name}(x) {
testCode = "(typeof($code) ${isTrue ? '==' : '!='} '$typeofName')";
}
}
- if (toType.isClass && toType is !ConcreteType) {
+ if (toType.isClass && toType is !ConcreteType
+ && !toType.isHiddenNativeType) {
toType.markUsed();
testCode = '($code instanceof ${toType.jsname})';
if (!isTrue) {
@@ -441,8 +457,9 @@ function \$assert_${toType.name}(x) {
// If we track nullability, we could simplify this check.
var temp = context.getTemp(this);
+ String checkName = 'is\$${toType.jsname}';
testCode = '(${context.assignTemp(temp, this).code} &&';
- testCode += ' ${temp.code}.is\$${toType.jsname})';
+ testCode += ' ${temp.code}.$checkName())';
if (isTrue) {
// Add !! to convert to boolean.
// TODO(jimhug): only do this if needed
@@ -453,6 +470,12 @@ function \$assert_${toType.name}(x) {
testCode = '!' + testCode;
}
if (this != temp) context.freeTemp(temp);
+
+ // Generate the fallback on Object (that returns false)
+ if (!world.objectType.varStubs.containsKey(checkName)) {
+ world.objectType.varStubs[checkName] =
+ new VarMethodStub(checkName, null, Arguments.EMPTY, 'return false');
+ }
}
return new Value(world.nonNullBool, testCode, span);
}
« frog/lib/corelib.dart ('K') | « frog/type.dart ('k') | frog/var_member.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698