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

Unified Diff: frog/member.dart

Issue 8763001: Fix names with '$' to not conflict with operators or internal helpers (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: merged again 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
« no previous file with comments | « frog/library.dart ('k') | frog/parser.dart » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: frog/member.dart
diff --git a/frog/member.dart b/frog/member.dart
index 5920acb26bae521fcbb4d44675fe3d6d76799929..f76e957d61be73ae4f861774196ed5c05bf760c7 100644
--- a/frog/member.dart
+++ b/frog/member.dart
@@ -36,7 +36,7 @@ class Parameter {
definition.value.span.start == definition.span.start) {
return;
}
- if (method.name == '\$call') {
+ if (method.name == ':call') {
// TODO(jimhug): Need simpler way to detect "true" function types vs.
// regular methods being used as function types for closures.
if (method.definition.body == null) {
@@ -108,8 +108,8 @@ class Member extends Element {
bool get isConst() => false;
bool get isFactory() => false;
- bool get isOperator() => name.startsWith('\$');
- bool get isCallMethod() => name == '\$call';
+ bool get isOperator() => name.startsWith(':');
+ bool get isCallMethod() => name == ':call';
bool get prefersPropertySyntax() => true;
bool get requiresFieldSyntax() => false;
@@ -162,13 +162,13 @@ class Member extends Element {
bool canInvoke(MethodGenerator context, Arguments args) {
// No source location needed because canInvoke may not produce errors.
return canGet &&
- new Value(returnType, null, null).canInvoke(context, '\$call', args);
+ new Value(returnType, null, null).canInvoke(context, ':call', args);
}
Value invoke(MethodGenerator context, Node node, Value target, Arguments args,
[bool isDynamic=false]) {
var newTarget = _get(context, node, target, isDynamic);
- return newTarget.invoke(context, '\$call', node, args, isDynamic);
+ return newTarget.invoke(context, ':call', node, args, isDynamic);
}
bool override(Member other) {
@@ -963,7 +963,7 @@ class MethodMember extends Member {
if (target is GlobalValue) {
target = target.dynamic.exp; // TODO: an inline "cast" would be nice.
}
- if (name == 'get\$length') {
+ if (name == 'get:length') {
if (target is ConstListValue || target is ConstMapValue) {
code = '${target.dynamic.values.length}';
}
@@ -975,7 +975,7 @@ class MethodMember extends Member {
}
// TODO(jmesserly): factor this better
- if (name == 'get\$typeName' && declaringType.library == world.dom) {
+ if (name == 'get:typeName' && declaringType.library == world.dom) {
world.gen.corejs.ensureTypeNameOf();
}
@@ -1120,13 +1120,13 @@ class MethodMember extends Member {
// TODO(jimhug): What about null?
if (!allConst) {
var code;
- if (name == '\$negate') {
+ if (name == ':negate') {
code = '-${target.code}';
- } else if (name == '\$bit_not') {
+ } else if (name == ':bit_not') {
code = '~${target.code}';
- } else if (name == '\$truncdiv' || name == '\$mod') {
+ } else if (name == ':truncdiv' || name == ':mod') {
world.gen.corejs.useOperator(name);
- code = '$name(${target.code}, ${argsCode[0]})';
+ code = '$jsname(${target.code}, ${argsCode[0]})';
} else {
var op = TokenKind.rawOperatorFromMethod(name);
code = '${target.code} $op ${argsCode[0]}';
@@ -1143,38 +1143,38 @@ class MethodMember extends Member {
ival1 = val1.toInt();
}
switch (name) {
- case '\$negate': value = -val0; break;
- case '\$add': value = val0 + val1; break;
- case '\$sub': value = val0 - val1; break;
- case '\$mul': value = val0 * val1; break;
- case '\$div': value = val0 / val1; break;
- case '\$truncdiv': value = val0 ~/ val1; break;
- case '\$mod': value = val0 % val1; break;
- case '\$eq': value = val0 == val1; break;
- case '\$lt': value = val0 < val1; break;
- case '\$gt': value = val0 > val1; break;
- case '\$lte': value = val0 <= val1; break;
- case '\$gte': value = val0 >= val1; break;
- case '\$ne': value = val0 != val1; break;
+ case ':negate': value = -val0; break;
+ case ':add': value = val0 + val1; break;
+ case ':sub': value = val0 - val1; break;
+ case ':mul': value = val0 * val1; break;
+ case ':div': value = val0 / val1; break;
+ case ':truncdiv': value = val0 ~/ val1; break;
+ case ':mod': value = val0 % val1; break;
+ case ':eq': value = val0 == val1; break;
+ case ':lt': value = val0 < val1; break;
+ case ':gt': value = val0 > val1; break;
+ case ':lte': value = val0 <= val1; break;
+ case ':gte': value = val0 >= val1; break;
+ case ':ne': value = val0 != val1; break;
// Note: unfortunatelly bit operations fail on doubles in dartvm
- case '\$bit_not': value = (~ival0).toDouble(); break;
- case '\$bit_or': value = (ival0 | ival1).toDouble(); break;
- case '\$bit_xor': value = (ival0 ^ ival1).toDouble(); break;
- case '\$bit_and': value = (ival0 & ival1).toDouble(); break;
- case '\$shl': value = (ival0 << ival1).toDouble(); break;
- case '\$sar': value = (ival0 >> ival1).toDouble(); break;
- case '\$shr': value = (ival0 >>> ival1).toDouble(); break;
+ case ':bit_not': value = (~ival0).toDouble(); break;
+ case ':bit_or': value = (ival0 | ival1).toDouble(); break;
+ case ':bit_xor': value = (ival0 ^ ival1).toDouble(); break;
+ case ':bit_and': value = (ival0 & ival1).toDouble(); break;
+ case ':shl': value = (ival0 << ival1).toDouble(); break;
+ case ':sar': value = (ival0 >> ival1).toDouble(); break;
+ case ':shr': value = (ival0 >>> ival1).toDouble(); break;
}
return new EvaluatedValue(inferredResult, value, "$value", node.span);
}
} else if (declaringType.isString) {
- if (name == '\$index') {
+ if (name == ':index') {
// Note: this could technically propagate constness, but that's not
// specified explicitly and the VM doesn't do that.
return new Value(declaringType, '${target.code}[${argsCode[0]}]',
node.span);
- } else if (name == '\$add') {
+ } else if (name == ':add') {
if (allConst) {
final value = _normConcat(target, args.values[0]);
return new EvaluatedValue(world.stringType, value, value, node.span);
@@ -1185,29 +1185,29 @@ class MethodMember extends Member {
node.span);
}
} else if (declaringType.isNative) {
- if (name == '\$index') {
+ if (name == ':index') {
// Note: this could technically propagate constness, but that's not
// specified explicitly and the VM doesn't do that.
return new Value(returnType, '${target.code}[${argsCode[0]}]', node.span);
- } else if (name == '\$setindex') {
+ } else if (name == ':setindex') {
return new Value(returnType,
'${target.code}[${argsCode[0]}] = ${argsCode[1]}', node.span);
}
}
// TODO(jimhug): Optimize null on lhs as well.
- if (name == '\$eq' || name == '\$ne') {
- final op = name == '\$eq' ? '==' : '!=';
+ if (name == ':eq' || name == ':ne') {
+ final op = name == ':eq' ? '==' : '!=';
- if (name == '\$ne') {
+ if (name == ':ne') {
// Ensure == is generated.
- target.invoke(context, '\$eq', node, args, isDynamic);
+ target.invoke(context, ':eq', node, args, isDynamic);
}
if (allConst) {
var val0 = target.dynamic.actualValue;
var val1 = args.values[0].dynamic.actualValue;
- var newVal = name == '\$eq' ? val0 == val1 : val0 != val1;
+ var newVal = name == ':eq' ? val0 == val1 : val0 != val1;
return new EvaluatedValue(world.nonNullBool,
newVal, "$newVal", node.span);
}
@@ -1220,8 +1220,8 @@ class MethodMember extends Member {
node.span);
}
world.gen.corejs.useOperator(name);
- return new Value(inferredResult, '$name(${target.code}, ${argsCode[0]})',
- node.span);
+ return new Value(inferredResult,
+ '$jsname(${target.code}, ${argsCode[0]})', node.span);
}
if (isCallMethod) {
@@ -1230,9 +1230,9 @@ class MethodMember extends Member {
'${target.code}(${Strings.join(argsCode, ", ")})', node.span);
}
- if (name == '\$index') {
+ if (name == ':index') {
world.gen.corejs.useIndex = true;
- } else if (name == '\$setindex') {
+ } else if (name == ':setindex') {
world.gen.corejs.useSetIndex = true;
}
@@ -1539,12 +1539,12 @@ class MemberSet {
}
if (returnValue.code == null) {
- if (name == '\$call') {
+ if (name == ':call') {
// TODO(jmesserly): reconcile this with similar code in Value
return target._varCall(context, args);
} else if (isOperator) {
// TODO(jmesserly): make operators less special.
- return target.invokeSpecial(name, args, returnValue.type);
+ return invokeSpecial(target, args, returnValue.type);
} else {
return invokeOnVar(context, node, target, args);
}
@@ -1553,6 +1553,28 @@ class MemberSet {
return returnValue;
}
+ Value invokeSpecial(Value target, Arguments args, Type returnType) {
+ assert(name.startsWith(':'));
+ assert(!args.hasNames);
+ // TODO(jimhug): We need to do this a little bit more like get and set on
+ // properties. We should check the set of members for something
+ // like "requiresNativeIndexer" and "requiresDartIndexer" to
+ // decide on a strategy.
+
+ var argsString = args.getCode();
+ // Most operator calls need to be emitted as function calls, so we don't
+ // box numbers accidentally. Indexing is the exception.
+ if (name == ':index' || name == ':setindex') {
+ return new Value(returnType, '${target.code}.$jsname($argsString)',
+ target.span);
+ } else {
+ if (argsString.length > 0) argsString = ', $argsString';
+ world.gen.corejs.useOperator(name);
+ return new Value(returnType, '$jsname(${target.code}$argsString)',
+ target.span);
+ }
+ }
+
Value invokeOnVar(MethodGenerator context, Node node, Value target,
Arguments args) {
var member = getVarMember(context, node, args);
« no previous file with comments | « frog/library.dart ('k') | frog/parser.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698