| OLD | NEW |
| 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2016, 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 library kernel.target.vm; | 4 library kernel.target.vm; |
| 5 | 5 |
| 6 import '../ast.dart'; | 6 import '../ast.dart'; |
| 7 import '../class_hierarchy.dart'; | 7 import '../class_hierarchy.dart'; |
| 8 import '../core_types.dart'; | 8 import '../core_types.dart'; |
| 9 import '../transformations/continuation.dart' as cont; | 9 import '../transformations/continuation.dart' as cont; |
| 10 import '../transformations/erasure.dart'; | 10 import '../transformations/erasure.dart'; |
| (...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 91 strongMode: strongMode, programRoots: flags.programRoots) | 91 strongMode: strongMode, programRoots: flags.programRoots) |
| 92 .transform(program); | 92 .transform(program); |
| 93 _hierarchy = null; // Hierarchy must be recomputed. | 93 _hierarchy = null; // Hierarchy must be recomputed. |
| 94 } | 94 } |
| 95 | 95 |
| 96 void performErasure(Program program) { | 96 void performErasure(Program program) { |
| 97 new Erasure().transform(program); | 97 new Erasure().transform(program); |
| 98 } | 98 } |
| 99 | 99 |
| 100 @override | 100 @override |
| 101 Expression instantiateInvocation(Member target, Expression receiver, | 101 Expression instantiateInvocation(CoreTypes coreTypes, Expression receiver, |
| 102 String name, Arguments arguments, int offset, bool isSuper) { | 102 String name, Arguments arguments, int offset, bool isSuper) { |
| 103 // See [_InvocationMirror] | 103 // See [_InvocationMirror] |
| 104 // (../../../../runtime/lib/invocation_mirror_patch.dart). | 104 // (../../../../runtime/lib/invocation_mirror_patch.dart). |
| 105 // The _InvocationMirror constructor takes the following arguments: | 105 // The _InvocationMirror constructor takes the following arguments: |
| 106 // * Method name (a string). | 106 // * Method name (a string). |
| 107 // * An arguments descriptor - a list consisting of: | 107 // * An arguments descriptor - a list consisting of: |
| 108 // - length of passed type argument vector, 0 if none passed. | 108 // - length of passed type argument vector, 0 if none passed. |
| 109 // - number of arguments (including receiver). | 109 // - number of arguments (including receiver). |
| 110 // - number of positional arguments (including receiver). | 110 // - number of positional arguments (including receiver). |
| 111 // - pairs (2 entries in the list) of | 111 // - pairs (2 entries in the list) of |
| (...skipping 23 matching lines...) Expand all Loading... |
| 135 argumentsList.add(argument.value); | 135 argumentsList.add(argument.value); |
| 136 } | 136 } |
| 137 | 137 |
| 138 Arguments constructorArguments = new Arguments([ | 138 Arguments constructorArguments = new Arguments([ |
| 139 new StringLiteral(name)..fileOffset = offset, | 139 new StringLiteral(name)..fileOffset = offset, |
| 140 _fixedLengthList(argumentsDescriptor, arguments.fileOffset), | 140 _fixedLengthList(argumentsDescriptor, arguments.fileOffset), |
| 141 _fixedLengthList(argumentsList, arguments.fileOffset), | 141 _fixedLengthList(argumentsList, arguments.fileOffset), |
| 142 new BoolLiteral(isSuper)..fileOffset = arguments.fileOffset, | 142 new BoolLiteral(isSuper)..fileOffset = arguments.fileOffset, |
| 143 ]); | 143 ]); |
| 144 | 144 |
| 145 return (target is Constructor | 145 return new ConstructorInvocation( |
| 146 ? new ConstructorInvocation(target, constructorArguments) | 146 coreTypes.invocationMirrorDefaultConstructor, constructorArguments) |
| 147 : new StaticInvocation(target, constructorArguments)) | |
| 148 ..fileOffset = offset; | 147 ..fileOffset = offset; |
| 149 } | 148 } |
| 150 | 149 |
| 151 Expression _fixedLengthList(List<Expression> elements, int charOffset) { | 150 @override |
| 151 Expression instantiateNoSuchMethodError(CoreTypes coreTypes, |
| 152 Expression receiver, String name, Arguments arguments, int offset, |
| 153 {bool isMethod: false, |
| 154 bool isGetter: false, |
| 155 bool isSetter: false, |
| 156 bool isField: false, |
| 157 bool isLocalVariable: false, |
| 158 bool isDynamic: false, |
| 159 bool isSuper: false, |
| 160 bool isStatic: false, |
| 161 bool isConstructor: false, |
| 162 bool isTopLevel: false}) { |
| 163 int type = _invocationType( |
| 164 isMethod: isMethod, |
| 165 isGetter: isGetter, |
| 166 isSetter: isSetter, |
| 167 isField: isField, |
| 168 isLocalVariable: isLocalVariable, |
| 169 isDynamic: isDynamic, |
| 170 isSuper: isSuper, |
| 171 isStatic: isStatic, |
| 172 isConstructor: isConstructor, |
| 173 isTopLevel: isTopLevel); |
| 174 return new ConstructorInvocation( |
| 175 coreTypes.noSuchMethodErrorImplementationConstructor, |
| 176 new Arguments(<Expression>[ |
| 177 receiver, |
| 178 new SymbolLiteral(name)..fileOffset = offset, |
| 179 new IntLiteral(type)..fileOffset = offset, |
| 180 _fixedLengthList(arguments.positional, arguments.fileOffset), |
| 181 new MapLiteral(new List<MapEntry>.from( |
| 182 arguments.named.map((NamedExpression arg) { |
| 183 return new MapEntry( |
| 184 new SymbolLiteral(arg.name)..fileOffset = arg.fileOffset, |
| 185 arg.value) |
| 186 ..fileOffset = arg.fileOffset; |
| 187 }))) |
| 188 ..fileOffset = arguments.fileOffset, |
| 189 new NullLiteral() |
| 190 ])); |
| 191 } |
| 192 |
| 193 int _invocationType( |
| 194 {bool isMethod: false, |
| 195 bool isGetter: false, |
| 196 bool isSetter: false, |
| 197 bool isField: false, |
| 198 bool isLocalVariable: false, |
| 199 bool isDynamic: false, |
| 200 bool isSuper: false, |
| 201 bool isStatic: false, |
| 202 bool isConstructor: false, |
| 203 bool isTopLevel: false}) { |
| 204 // This is copied from [_InvocationMirror]( |
| 205 // ../../../../../../runtime/lib/invocation_mirror_patch.dart). |
| 206 |
| 207 // Constants describing the invocation type. |
| 208 // _FIELD cannot be generated by regular invocation mirrors. |
| 209 const int _METHOD = 0; |
| 210 const int _GETTER = 1; |
| 211 const int _SETTER = 2; |
| 212 const int _FIELD = 3; |
| 213 const int _LOCAL_VAR = 4; |
| 214 // ignore: UNUSED_LOCAL_VARIABLE |
| 215 const int _TYPE_SHIFT = 0; |
| 216 const int _TYPE_BITS = 3; |
| 217 // ignore: UNUSED_LOCAL_VARIABLE |
| 218 const int _TYPE_MASK = (1 << _TYPE_BITS) - 1; |
| 219 |
| 220 // These values, except _DYNAMIC and _SUPER, are only used when throwing |
| 221 // NoSuchMethodError for compile-time resolution failures. |
| 222 const int _DYNAMIC = 0; |
| 223 const int _SUPER = 1; |
| 224 const int _STATIC = 2; |
| 225 const int _CONSTRUCTOR = 3; |
| 226 const int _TOP_LEVEL = 4; |
| 227 const int _CALL_SHIFT = _TYPE_BITS; |
| 228 const int _CALL_BITS = 3; |
| 229 // ignore: UNUSED_LOCAL_VARIABLE |
| 230 const int _CALL_MASK = (1 << _CALL_BITS) - 1; |
| 231 |
| 232 int type = -1; |
| 233 // For convenience, [isGetter] and [isSetter] takes precedence over |
| 234 // [isMethod]. |
| 235 if (isGetter) { |
| 236 type = _GETTER; |
| 237 } else if (isSetter) { |
| 238 type = _SETTER; |
| 239 } else if (isMethod) { |
| 240 type = _METHOD; |
| 241 } else if (isField) { |
| 242 type = _FIELD; |
| 243 } else if (isLocalVariable) { |
| 244 type = _LOCAL_VAR; |
| 245 } |
| 246 |
| 247 if (isDynamic) { |
| 248 type |= (_DYNAMIC << _CALL_SHIFT); |
| 249 } else if (isSuper) { |
| 250 type |= (_SUPER << _CALL_SHIFT); |
| 251 } else if (isStatic) { |
| 252 type |= (_STATIC << _CALL_SHIFT); |
| 253 } else if (isConstructor) { |
| 254 type |= (_CONSTRUCTOR << _CALL_SHIFT); |
| 255 } else if (isTopLevel) { |
| 256 type |= (_TOP_LEVEL << _CALL_SHIFT); |
| 257 } |
| 258 |
| 259 return type; |
| 260 } |
| 261 |
| 262 Expression _fixedLengthList(List<Expression> elements, int offset) { |
| 152 // TODO(ahe): It's possible that it would be better to create a fixed-length | 263 // TODO(ahe): It's possible that it would be better to create a fixed-length |
| 153 // list first, and then populate it. That would create fewer objects. But as | 264 // list first, and then populate it. That would create fewer objects. But as |
| 154 // this is currently only used in (statically resolved) no-such-method | 265 // this is currently only used in (statically resolved) no-such-method |
| 155 // handling, the current approach seems sufficient. | 266 // handling, the current approach seems sufficient. |
| 156 return new MethodInvocation( | 267 return new MethodInvocation( |
| 157 new ListLiteral(elements)..fileOffset = charOffset, | 268 new ListLiteral(elements)..fileOffset = offset, |
| 158 new Name("toList"), | 269 new Name("toList"), |
| 159 new Arguments(<Expression>[], named: <NamedExpression>[ | 270 new Arguments(<Expression>[], named: <NamedExpression>[ |
| 160 new NamedExpression("growable", new BoolLiteral(false)) | 271 new NamedExpression("growable", new BoolLiteral(false)) |
| 161 ])); | 272 ])); |
| 162 } | 273 } |
| 163 } | 274 } |
| OLD | NEW |